v2.0.0
Loading...
Searching...
No Matches
channelselectionview.cpp
Go to the documentation of this file.
1//=============================================================================================================
16
17//=============================================================================================================
18// INCLUDES
19//=============================================================================================================
20
22#include "ui_channelselectionview.h"
26
27#include <utils/layoutloader.h>
28#include <utils/selectionio.h>
29#include <utils/layoutmaker.h>
30
31#include <fiff/fiff.h>
32
33//=============================================================================================================
34// STL INCLUDES
35//=============================================================================================================
36
37#include <iostream>
38
39//=============================================================================================================
40// QT INCLUDES
41//=============================================================================================================
42
43#include <QDate>
44#include <QVector3D>
45#include <QFileDialog>
46#include <QFileInfo>
47#include <QListWidgetItem>
48#include <QSettings>
49#include <QApplication>
50#include <QKeyEvent>
51#include <QSignalBlocker>
52
53//=============================================================================================================
54// EIGEN INCLUDES
55//=============================================================================================================
56
57//=============================================================================================================
58// USED NAMESPACES
59//=============================================================================================================
60
61using namespace DISPLIB;
62using namespace FIFFLIB;
63using namespace UTILSLIB;
64
65//=============================================================================================================
66// DEFINE MEMBER METHODS
67//=============================================================================================================
68
69ChannelSelectionView::ChannelSelectionView(const QString& sSettingsPath,
70 QWidget *parent,
71 ChannelInfoModel::SPtr pChannelInfoModel,
72 Qt::WindowType f)
73: AbstractView(parent, f)
74, m_pUi(new Ui::ChannelSelectionViewWidget)
75, m_pChannelInfoModel(pChannelInfoModel)
76, m_bSetup(false)
77{
78 m_sSettingsPath = sSettingsPath;
79 m_pUi->setupUi(this);
80
81 //Init gui elements
82 initListWidgets();
83 initSelectionSceneView();
84 initComboBoxes();
85 initButtons();
86 initCheckBoxes();
87
89
90 m_bSetup = true;
91
92 setCurrentlyMappedFiffChannels(m_pChannelInfoModel->getMappedChannelsList());
93}
94
95//=============================================================================================================
96
98{
99// saveSettings();
100
101 delete m_pUi;
102}
103
104//=============================================================================================================
105
106void ChannelSelectionView::initListWidgets()
107{
108 //Install event filter to receive key press events
109 m_pUi->m_listWidget_userDefined->installEventFilter(this);
110 m_pUi->m_listWidget_selectionGroups->installEventFilter(this);
111
112 //Connect list widgets to update themselves and other list widgets when changed
113 connect(m_pUi->m_listWidget_selectionGroups, &QListWidget::currentItemChanged,
114 this, &ChannelSelectionView::updateSelectionGroupsList);
115
116 //Update data view whenever a drag and drop item movement is performed
117 //TODO: This is inefficient because updateDataView is called everytime the list's viewport is entered
118 connect(m_pUi->m_listWidget_userDefined->model(), &QAbstractTableModel::dataChanged,
120}
121
122//=============================================================================================================
123
124void ChannelSelectionView::initSelectionSceneView()
125{
126 //Create layout scene and set to view
127 m_pSelectionScene = new SelectionScene(m_pUi->m_graphicsView_layoutPlot);
128 m_pUi->m_graphicsView_layoutPlot->setScene(m_pSelectionScene);
129
130 connect(m_pSelectionScene, &QGraphicsScene::selectionChanged,
131 this, &ChannelSelectionView::updateUserDefinedChannelsList);
132}
133
134//=============================================================================================================
135
136void ChannelSelectionView::initComboBoxes()
137{
138 m_pUi->m_comboBox_layoutFile->clear();
139 m_pUi->m_comboBox_layoutFile->insertItems(0, QStringList()
140 << "babymeg-mag-inner-layer.lout"
141 << "babymeg-mag-outer-layer.lout"
142// << "babymeg-mag-ref.lout"
143 << "Vectorview-grad.lout"
144 << "Vectorview-all.lout"
145 << "Vectorview-mag.lout"
146 << "standard_waveguard64_duke.lout"
147// << "CTF-275.lout"
148// << "magnesWH3600.lout"
149 );
150
151 connect(m_pUi->m_comboBox_layoutFile, &QComboBox::currentTextChanged,
152 this, &ChannelSelectionView::onComboBoxLayoutChanged);
153
154 //Initialise layout as neuromag vectorview with all channels
155 QString selectionName("Vectorview-all.lout");
156 //loadLayout(QCoreApplication::applicationDirPath() + selectionName.prepend("/../resources/general/2DLayouts/"));
157 setCurrentLayoutFile(selectionName);
158
159 //Load selection groups again because they need to be reinitialised every time a new layout hase been loaded
160 selectionName = QString("mne_browse_raw_vv.sel");
161 loadSelectionGroups(QCoreApplication::applicationDirPath() + selectionName.prepend("/../resources/general/selectionGroups/"));
162}
163
164//=============================================================================================================
165
166void ChannelSelectionView::initButtons()
167{
168 connect(m_pUi->m_pushButton_saveSelection, &QPushButton::clicked,
169 this, &ChannelSelectionView::onBtnSaveUserSelection);
170
171 connect(m_pUi->m_pushButton_loadSelection, &QPushButton::clicked,
172 this, &ChannelSelectionView::onBtnLoadUserSelection);
173
174 connect(m_pUi->m_pushButton_addToSelectionGroups, &QPushButton::clicked,
175 this, &ChannelSelectionView::onBtnAddToSelectionGroups);
176}
177
178//=============================================================================================================
179
180void ChannelSelectionView::initCheckBoxes()
181{
182 connect(m_pUi->m_checkBox_showBadChannelsAsRed, &QCheckBox::clicked,
184}
185
186//=============================================================================================================
187
188void ChannelSelectionView::setCurrentlyMappedFiffChannels(const QStringList &mappedLayoutChNames)
189{
190 m_currentlyLoadedFiffChannels = mappedLayoutChNames;
191
192 //Clear the visible channel list
193 m_pUi->m_listWidget_visibleChannels->clear();
194
195 //Keep the entry All in the selection list and m_selectionGroupsMap -> delete the rest
196 m_pUi->m_listWidget_selectionGroups->clear();
197
198 //Create group 'All' manually (because this group depends on the loaded channels from the fiff data file, not on the loaded selection file)
199 auto it = m_selectionGroupsMap.find("All");
200 if (it != m_selectionGroupsMap.end()) {
201 m_selectionGroupsMap.erase(it);
202 }
203 m_selectionGroupsMap.insert("All", m_currentlyLoadedFiffChannels);
204
205 //Add selection groups to list widget
206 for(auto i = m_selectionGroupsMap.constBegin(); i != m_selectionGroupsMap.constEnd(); i++) {
207 m_pUi->m_listWidget_selectionGroups->insertItem(m_pUi->m_listWidget_selectionGroups->count(), i.key());
208 }
209
210 //Set group all as slected item
211 m_pUi->m_listWidget_selectionGroups->setCurrentItem(getItemForChName(m_pUi->m_listWidget_selectionGroups, "All"), QItemSelectionModel::Select);
212
213 //Update selection
214 updateSelectionGroupsList(getItemForChName(m_pUi->m_listWidget_selectionGroups, "All"), new QListWidgetItem());
215}
216
217//=============================================================================================================
218
219void ChannelSelectionView::highlightChannels(QModelIndexList channelIndexList)
220{
221 QStringList channelList;
222 for(int i = 0; i < channelIndexList.size(); i++) {
223 QModelIndex nameIndex = m_pChannelInfoModel->index(channelIndexList.at(i).row(),3);
224 channelList<<m_pChannelInfoModel->data(nameIndex, ChannelInfoModelRoles::GetMappedLayoutChName).toString();
225 }
226
227 QList<QGraphicsItem *> allSceneItems = m_pSelectionScene->items();
228
229 for(int i = 0; i < allSceneItems.size(); i++) {
230 SelectionSceneItem* item = static_cast<SelectionSceneItem*>(allSceneItems.at(i));
231 if(channelList.contains(item->m_sChannelName))
232 item->m_bHighlightItem = true;
233 else
234 item->m_bHighlightItem = false;
235 }
236
237 m_pSelectionScene->update();
238}
239
240//=============================================================================================================
241
242void ChannelSelectionView::selectChannels(QStringList channelList)
243{
244 QList<QGraphicsItem *> allSceneItems = m_pSelectionScene->items();
245
246 for(int i = 0; i < allSceneItems.size(); i++) {
247 SelectionSceneItem* item = static_cast<SelectionSceneItem*>(allSceneItems.at(i));
248 if(channelList.contains(item->m_sChannelName))
249 item->setSelected(true);
250 else
251 item->setSelected(false);
252 }
253
254 m_pSelectionScene->update();
255}
256
257//=============================================================================================================
258
260{
261 //if no channels have been selected by the user -> show selected group channels
262 QListWidget* targetListWidget;
263 if(m_pUi->m_listWidget_userDefined->count()>0)
264 targetListWidget = m_pUi->m_listWidget_userDefined;
265 else
266 targetListWidget = m_pUi->m_listWidget_visibleChannels;
267
268 //Create list of channels which are to be visible in the view
269 QStringList selectedChannels;
270
271 for(int i = 0; i < targetListWidget->count(); i++) {
272 QListWidgetItem* item = targetListWidget->item(i);
273 selectedChannels << item->text();
274 }
275
276 return selectedChannels;
277}
278
279//=============================================================================================================
280
281QListWidgetItem* ChannelSelectionView::getItemForChName(QListWidget* listWidget,
282 const QString &channelName)
283{
284 for(int i=0; i < listWidget->count(); i++)
285 if(listWidget->item(i)->text() == channelName)
286 return listWidget->item(i);
287
288 return new QListWidgetItem();
289}
290
291//=============================================================================================================
292
293const QMap<QString,QPointF>& ChannelSelectionView::getLayoutMap()
294{
295 return m_layoutMap;
296}
297
298//=============================================================================================================
299
300void ChannelSelectionView::newFiffFileLoaded(QSharedPointer<FiffInfo> &pFiffInfo)
301{
302 Q_UNUSED(pFiffInfo);
303
304 loadLayout(resolveLayoutPath(m_pUi->m_comboBox_layoutFile->currentText()));
305}
306
307//=============================================================================================================
308
310{
311 return m_pUi->m_comboBox_layoutFile->currentText();
312}
313
314//=============================================================================================================
315
317{
318 return m_pUi->m_lineEdit_loadedFile->text();
319}
320
321//=============================================================================================================
322
323void ChannelSelectionView::setCurrentLayoutFile(QString currentLayoutFile)
324{
325 qDebug() << "setCurrentLayoutFile:" << currentLayoutFile;
326 const QSignalBlocker blocker(m_pUi->m_comboBox_layoutFile);
327 m_pUi->m_comboBox_layoutFile->setCurrentText(currentLayoutFile);
328
329 loadLayout(resolveLayoutPath(currentLayoutFile));
331}
332
333//=============================================================================================================
334
336{
337 QStringList badChannelMappedNames;
338 QStringList badChannelList = m_pChannelInfoModel->getBadChannelList();
339
340 if(m_pUi->m_checkBox_showBadChannelsAsRed->isChecked()) {
341 for(int i = 0; i < m_pChannelInfoModel->rowCount(); i++) {
342 QModelIndex digIndex = m_pChannelInfoModel->index(i,3);
343 QString mappedChName = m_pChannelInfoModel->data(digIndex,ChannelInfoModelRoles::GetMappedLayoutChName).toString();
344
345 digIndex = m_pChannelInfoModel->index(i,1);
346 QString origChName = m_pChannelInfoModel->data(digIndex,ChannelInfoModelRoles::GetOrigChName).toString();
347
348 if(badChannelList.contains(origChName)) {
349 badChannelMappedNames << mappedChName;
350 }
351 }
352 }
353
354 m_pSelectionScene->repaintItems(m_layoutMap, badChannelMappedNames);
355 m_pSelectionScene->update();
356
357 updateSceneItems();
359}
360
361//=============================================================================================================
362
364{
365 //if no channels have been selected by the user -> show selected group channels
366 QListWidget* targetListWidget;
367 if(m_pUi->m_listWidget_userDefined->count()>0)
368 targetListWidget = m_pUi->m_listWidget_userDefined;
369 else
370 targetListWidget = m_pUi->m_listWidget_visibleChannels;
371
372 //Create list of channels which are to be visible in the view
373 QStringList selectedChannels;
374
375 for(int i = 0; i < targetListWidget->count(); i++) {
376 QListWidgetItem* item = targetListWidget->item(i);
377 int indexTemp = m_pChannelInfoModel->getIndexFromMappedChName(item->text());
378
379 if(indexTemp != -1) {
380 QModelIndex mappedNameIndex = m_pChannelInfoModel->index(indexTemp,1);
381 QString origChName = m_pChannelInfoModel->data(mappedNameIndex,ChannelInfoModelRoles::GetOrigChName).toString();
382
383 selectedChannels << origChName;
384 }
385 else
386 selectedChannels << item->text();
387 }
388
389 emit showSelectedChannelsOnly(selectedChannels);
390
391 //emit signal that selection was changed
392 if(!m_pSelectionScene->selectedItems().empty()) {
393 emit selectionChanged(m_pSelectionScene->selectedItems());
394 } else {
395 //only return visible items (EEG or MEG channels)
396 QList<QGraphicsItem*> visibleItemList = m_pSelectionScene->items();
397 QMutableListIterator<QGraphicsItem*> i(visibleItemList);
398 while (i.hasNext()) {
399 if(!i.next()->isVisible()){
400 i.remove();
401 }
402 }
403 emit selectionChanged(visibleItemList);
404 }
405}
406
407//=============================================================================================================
408
410{
411 if(m_sSettingsPath.isEmpty()) {
412 return;
413 }
414
415 QSettings settings("MNECPP");
416
417 std::cout << "saveSettings: " << getCurrentLayoutFile().toStdString();
418
419 settings.setValue(m_sSettingsPath + QString("/ChannelSelectionView/selectedLayoutFile"), getCurrentLayoutFile());
420 settings.setValue(m_sSettingsPath + QString("/ChannelSelectionView/channelSelectionViewPos"), this->pos());
421 settings.setValue(m_sSettingsPath + QString("/ChannelSelectionView/selectedGroupFile"), getCurrentGroupFile());
422}
423
424//=============================================================================================================
425
427{
428 if(m_sSettingsPath.isEmpty()) {
429 return;
430 }
431
432 QSettings settings("MNECPP");
433
434 setCurrentLayoutFile(settings.value(m_sSettingsPath + QString("/ChannelSelectionView/selectedLayoutFile"), "Vectorview-all.lout").toString());
435 loadSelectionGroups(QCoreApplication::applicationDirPath() + settings.value(m_sSettingsPath + QString("/ChannelSelectionView/selectedGroupFile"), "mne_browse_raw_vv.sel").toString().prepend("/../resources/general/selectionGroups/"));
436
437 qDebug() << "loadSettings: " << getCurrentLayoutFile();
438
439 QPoint pos = settings.value(m_sSettingsPath + QString("/ChannelSelectionView/channelSelectionViewPos"), QPoint(100,100)).toPoint();
440
441 QList<QScreen*> screensList = QGuiApplication::screens();
442 if(screensList.isEmpty())
443 {
444 move(QPoint(100,100));
445 } else {
446 move(pos);
447 }
448}
449
450//=============================================================================================================
451
453{
454 switch(mode) {
456 break;
457 default: // default is research mode
458 break;
459 }
460}
461
462//=============================================================================================================
463
465{
466 switch(mode) {
468 break;
469 default: // default is realtime mode
470 break;
471 }
472}
473
474//=============================================================================================================
475
476bool ChannelSelectionView::loadLayout(QString path)
477{
478 qDebug() << "loadLayout:" << path;
479 bool state = LayoutLoader::readMNELoutFile(path, m_layoutMap);
480
481 //if no layout for EEG is specified generate from digitizer points
482 QList<QVector<float> > inputPoints;
483 QList<QVector<float> > outputPoints;
484 QStringList names;
485 QFile out("manualLayout.lout");
486
487 for(int i = 0; i < m_pChannelInfoModel->rowCount(); i++) {
488 QModelIndex digIndex = m_pChannelInfoModel->index(i,1);
489 QString chName = m_pChannelInfoModel->data(digIndex,ChannelInfoModelRoles::GetOrigChName).toString();
490
491 digIndex = m_pChannelInfoModel->index(i,8);
492 QVector3D channelDig = m_pChannelInfoModel->data(digIndex,ChannelInfoModelRoles::GetChDigitizer).value<QVector3D>();
493
494 digIndex = m_pChannelInfoModel->index(i,4);
495 int kind = m_pChannelInfoModel->data(digIndex,ChannelInfoModelRoles::GetChKind).toInt();
496
497 if(kind == FIFFV_EEG_CH) { //FIFFV_MEG_CH
498 QVector<float> temp;
499 temp.append(channelDig.x());
500 temp.append(channelDig.y());
501 temp.append(-channelDig.z());
502 inputPoints.append(temp);
503
504 names<<chName;
505 }
506 }
507
508 float prad = 60.0;
509 float width = 5.0;
510 float height = 4.0;
511 int numberTries = 0;
512
513 if(inputPoints.size() > 0) {
514 while(numberTries < 10) {
515 if(!LayoutMaker::makeLayout(inputPoints,
516 outputPoints,
517 names,
518 out,
519 true,
520 prad,
521 width,
522 height,
523 false,
524 true,
525 false)) {
526 numberTries++;
527 } else {
528 numberTries = 11;
529 }
530 }
531 }
532
533 //Add new EEG points to Layout Map
534 for(int i = 0; i < outputPoints.size(); i++) {
535 if(!m_layoutMap.contains(names.at(i))) {
536 m_layoutMap[names.at(i)] = QPointF(outputPoints.at(i)[0],outputPoints.at(i)[1]);
537 }
538 }
539
540 QStringList bad;
541 m_pSelectionScene->repaintItems(m_layoutMap, bad);
542 m_pSelectionScene->update();
543 updateSceneItems();
544
545 //Fit to view
546 m_pUi->m_graphicsView_layoutPlot->fitInView(m_pSelectionScene->itemsBoundingRect(), Qt::KeepAspectRatio);
547
548 if(state)
549 emit loadedLayoutMap(m_layoutMap);
550
551 if(m_bSetup){
552 saveSettings();
553 }
554
555 return state;
556}
557
558//=============================================================================================================
559
560QString ChannelSelectionView::resolveLayoutPath(const QString& layoutFile) const
561{
562 if(layoutFile.isEmpty()) {
563 return QString();
564 }
565
566 if(QFileInfo(layoutFile).isAbsolute()) {
567 return layoutFile;
568 }
569
570 return QCoreApplication::applicationDirPath()
571 + QStringLiteral("/../resources/general/2DLayouts/")
572 + layoutFile;
573}
574
575//=============================================================================================================
576
577bool ChannelSelectionView::loadSelectionGroups(QString path)
578{
579
580 //Clear the visible channel list
581 m_pUi->m_listWidget_visibleChannels->clear();
582
583 //Keep the entry All in the selection list and m_selectionGroupsMap -> delete the rest
584 m_pUi->m_listWidget_selectionGroups->clear();
585
586 //Read selection from file and store to map
587 QString newPath = path; //QCoreApplication::applicationDirPath() + path.prepend("/../resources/general/selectionGroups/");
588
589 m_selectionGroupsMap.clear();
590
591 bool state;
592 if(!path.isEmpty()) {
593 if(path.contains(".sel"))
594 state = SelectionIO::readMNESelFile(newPath, m_selectionGroupsMap);
595 if(path.contains(".mon"))
596 state = SelectionIO::readBrainstormMonFile(newPath, m_selectionGroupsMap);
597 }
598
599 //Create group 'All' and 'All EEG' manually (bcause this group depends on the loaded channels from the Info data file, not on the loaded selection file)
600 auto it = m_selectionGroupsMap.find("All");
601 if (it != m_selectionGroupsMap.end()) {
602 m_selectionGroupsMap.erase(it);
603 }
604 m_selectionGroupsMap.insert("All", m_currentlyLoadedFiffChannels);
605
606 QStringList names;
607 for(int i = 0; i < m_pChannelInfoModel->rowCount(); i++) {
608 QModelIndex digIndex = m_pChannelInfoModel->index(i,1);
609 QString chName = m_pChannelInfoModel->data(digIndex,ChannelInfoModelRoles::GetOrigChName).toString();
610
611 digIndex = m_pChannelInfoModel->index(i,4);
612 int kind = m_pChannelInfoModel->data(digIndex,ChannelInfoModelRoles::GetChKind).toInt();
613
614 if(kind == FIFFV_EEG_CH) //FIFFV_MEG_CH
615 names<<chName;
616 }
617
618 //Add 'Add EEG' group to selection groups
619 it = m_selectionGroupsMap.find("All EEG");
620 if (it != m_selectionGroupsMap.end()) {
621 m_selectionGroupsMap.erase(it);
622 }
623 m_selectionGroupsMap.insert("All EEG", names);
624
625 //Add selection groups to list widget
626
627 for(auto i = m_selectionGroupsMap.constBegin(); i != m_selectionGroupsMap.constEnd(); i++) {
628 m_pUi->m_listWidget_selectionGroups->insertItem(m_pUi->m_listWidget_selectionGroups->count(), i.key());
629 }
630
631 //Update selection
632 updateSelectionGroupsList(getItemForChName(m_pUi->m_listWidget_selectionGroups, "All"), new QListWidgetItem());
633
634 //Set group all as slected item
635 m_pUi->m_listWidget_selectionGroups->setCurrentItem(getItemForChName(m_pUi->m_listWidget_selectionGroups, "All"), QItemSelectionModel::Select);
636
637 m_pUi->m_lineEdit_loadedFile->setText(QFileInfo(path).fileName());
638
639 if(m_bSetup){
640 saveSettings();
641 }
642
643 return state;
644}
645
646//=============================================================================================================
647
648void ChannelSelectionView::cleanUpMEGChannels()
649{
650 //Iterate through all loaded selection groups
651 for(auto i = m_selectionGroupsMap.constBegin(); i != m_selectionGroupsMap.constEnd(); i++) {
652 QStringList channelList = i.value();
653
654 //Search the current selection group for MEG channels which are not in the currently loaded layout file and delete them
655 QMutableStringListIterator stringListIndex(channelList);
656 while (stringListIndex.hasNext()) {
657 stringListIndex.next();
658
659 if(!m_layoutMap.contains(stringListIndex.value()) && stringListIndex.value().contains("MEG"))
660 stringListIndex.remove();
661 }
662
663 //Overwrite old selection groups channels
664 m_selectionGroupsMap.insert(i.key(), channelList);
665 }
666}
667
668//=============================================================================================================
669
670void ChannelSelectionView::updateSelectionGroupsList(QListWidgetItem* current, QListWidgetItem* previous)
671{
672 Q_UNUSED(previous);
673
674 if(current == 0){
675 return;
676 }
677 if(current->text().contains("EEG"))
678 m_pSelectionScene->m_iChannelTypeMode = FIFFV_EEG_CH;
679 else
680 m_pSelectionScene->m_iChannelTypeMode = FIFFV_MEG_CH;
681
682 //update visible channel list widget
683 m_pUi->m_listWidget_visibleChannels->clear();
684 auto items = m_selectionGroupsMap.find(current->text());
685 m_pUi->m_listWidget_visibleChannels->addItems(*items);
686
687 //update scene items based o nthe new selection group
688 updateSceneItems();
689
690 //update the channels plotted in the data view
692
694}
695
696//=============================================================================================================
697
698void ChannelSelectionView::updateSceneItems()
699{
700 QStringList visibleItems;
701
702 for(int i = 0; i < m_pUi->m_listWidget_visibleChannels->count(); i++)
703 visibleItems << m_pUi->m_listWidget_visibleChannels->item(i)->text();
704
705 m_pSelectionScene->hideItems(visibleItems);
706}
707
708//=============================================================================================================
709
710void ChannelSelectionView::updateUserDefinedChannelsList()
711{
712 QList<QGraphicsItem*> itemList = m_pSelectionScene->selectedItems();
713 QStringList userDefinedChannels;
714
715 for(int i = 0; i < itemList.size(); i++) {
716 SelectionSceneItem* item = static_cast<SelectionSceneItem*>(itemList.at(i));
717 userDefinedChannels << item->m_sChannelName;
718 }
719
720 m_pUi->m_listWidget_userDefined->clear();
721 m_pUi->m_listWidget_userDefined->addItems(userDefinedChannels);
722
724}
725
726//=============================================================================================================
727
728void ChannelSelectionView::onBtnLoadUserSelection()
729{
730 QString path = QFileDialog::getOpenFileName(this,
731 QString("Open selection file"),
732 QString("../resources/general/selectionGroups/"),
733 tr("Selection files (*.sel *.mon)"));
734
735 if(path.isEmpty())
736 return;
737
738 loadSelectionGroups(path);
739 m_pUi->m_lineEdit_loadedFile->setText(QFileInfo(path).fileName());
740}
741
742//=============================================================================================================
743
744void ChannelSelectionView::onBtnSaveUserSelection()
745{
746 QDate date;
747 QString path = QFileDialog::getSaveFileName(this,
748 "Save user channel selection",
749 QString("../resources/general/selectionGroups/%1_%2_%3_UserSelection").arg(date.currentDate().year()).arg(date.currentDate().month()).arg(date.currentDate().day()),
750 tr("MNE selection file(*.sel);; Brainstorm montage file(*.mon)"));
751
752 QMultiMap<QString, QStringList> tempMap = m_selectionGroupsMap;
753 tempMap.remove("All");
754 tempMap.remove("All EEG");
755
756 if(!path.isEmpty()) {
757 if(path.contains(".sel"))
758 SelectionIO::writeMNESelFile(path, tempMap);
759 if(path.contains(".mon"))
761 }
762}
763
764//=============================================================================================================
765
766void ChannelSelectionView::onBtnAddToSelectionGroups()
767{
768 QStringList temp;
769 for(int i = 0; i < m_pUi->m_listWidget_userDefined->count(); i++)
770 temp<<m_pUi->m_listWidget_userDefined->item(i)->text();
771
772 m_selectionGroupsMap.insert(m_pUi->m_lineEdit_selectionGroupName->text(), temp);
773 m_pUi->m_listWidget_selectionGroups->insertItem(m_pUi->m_listWidget_selectionGroups->count(), m_pUi->m_lineEdit_selectionGroupName->text());
774}
775
776//=============================================================================================================
777
778void ChannelSelectionView::onComboBoxLayoutChanged()
779{
780 QString selectionName(m_pUi->m_comboBox_layoutFile->currentText());
781 loadLayout(resolveLayoutPath(selectionName));
783}
784
785//=============================================================================================================
786
787void ChannelSelectionView::resizeEvent(QResizeEvent* event)
788{
789 Q_UNUSED(event);
790
791 //Fit scene in view
792 //m_pUi->m_graphicsView_layoutPlot->fitInView(m_pSelectionScene->itemsBoundingRect(), Qt::KeepAspectRatio);
793}
794
795//=============================================================================================================
796
797bool ChannelSelectionView::eventFilter(QObject *obj, QEvent *event)
798{
799 //Setup delete key on user defined channel list
800 if (obj == m_pUi->m_listWidget_userDefined && event->type() == QEvent::KeyRelease) {
801 QKeyEvent *keyEvent = static_cast<QKeyEvent*>(event);
802
803 if(keyEvent->key() == Qt::Key_Delete) {
804 qDeleteAll(m_pUi->m_listWidget_userDefined->selectedItems());
806 return true;
807 }
808 else
809 return false;
810 }
811
812 if (obj == m_pUi->m_listWidget_selectionGroups && event->type() == QEvent::KeyRelease) {
813 QKeyEvent *keyEvent = static_cast<QKeyEvent*>(event);
814
815 if(keyEvent->key() == Qt::Key_Delete) {
816 QList<QListWidgetItem *> tempSelectedList;
817
818 for(int i = 0; i < m_pUi->m_listWidget_selectionGroups->selectedItems().size(); i++) {
819 if(m_pUi->m_listWidget_selectionGroups->selectedItems().at(i)->text() != "All" &&
820 m_pUi->m_listWidget_selectionGroups->selectedItems().at(i)->text() != "All EEG") {
821 tempSelectedList.append(m_pUi->m_listWidget_selectionGroups->selectedItems().at(i));
822 m_selectionGroupsMap.remove(m_pUi->m_listWidget_selectionGroups->selectedItems().at(i)->text());
823 }
824 }
825
826 qDeleteAll(tempSelectedList);
828
829 return true;
830 }
831 else
832 return false;
833 }
834
835 // pass the event on to the parent class
836 return QWidget::eventFilter(obj, event);
837}
838
839//=============================================================================================================
840
842{
843 return m_pUi->viewWidget;
844}
845
846//=============================================================================================================
847
849{
850 return m_pUi->controlWidget;
851}
852
853//=============================================================================================================
854
856{
857 return ((m_pUi->m_listWidget_selectionGroups->currentItem()->text() == "All") && (m_pUi->m_listWidget_userDefined->count() == 0));
858}
859
860//=============================================================================================================
861
863{
864 m_pSelectionScene->clear();
865}
Reader for ANT .elc electrode files and MNE .lout 2-D channel layouts used by the topographic plottin...
Reader / writer for MNE .sel channel-selection files and Brainstorm .mon montage files.
Generator that projects 3-D electrode positions onto a 2-D .lout topographic layout via least-squares...
QAbstractTableModel exposing per-channel FIFF metadata (name, type, unit, position,...
Channel-selection group descriptor (SelectionItem) and the matching QGraphicsItem (SelectionSceneItem...
QGraphicsScene of the sensor-layout dots used by ChannelSelectionView for interactive channel picking...
Interactive 2-D sensor-layout picker for building and saving channel groups.
#define FIFFV_EEG_CH
#define FIFFV_MEG_CH
Static MATLAB-style FIFF facade: thin wrapper functions kept for parity with the historical mne-matla...
FIFF file I/O, in-memory data structures and high-level readers/writers.
2-D display widgets and visualisation helpers (charts, topography, colour maps).
Shared utilities (I/O helpers, spectral analysis, layout management, warp algorithms).
AbstractView(QWidget *parent=0, Qt::WindowFlags f=Qt::Widget)
void selectionChanged(const QList< QGraphicsItem * > &selectedChannelItems)
QListWidgetItem * getItemForChName(QListWidget *listWidget, const QString &channelName)
const QMap< QString, QPointF > & getLayoutMap()
void showSelectedChannelsOnly(QStringList selectedChannels)
void updateProcessingMode(ProcessingMode mode)
ChannelSelectionView(const QString &sSettingsPath="", QWidget *parent=0, QSharedPointer< ChannelInfoModel > pChannelInfoModel=QSharedPointer< ChannelInfoModel >(0), Qt::WindowType f=Qt::Widget)
void highlightChannels(QModelIndexList channelIndexList)
void newFiffFileLoaded(QSharedPointer< FIFFLIB::FiffInfo > &pFiffInfo)
void selectChannels(QStringList channelList)
void setCurrentlyMappedFiffChannels(const QStringList &mappedLayoutChNames)
void loadedLayoutMap(const QMap< QString, QPointF > &layoutMap)
void setCurrentLayoutFile(QString currentLayoutFile)
QSharedPointer< ChannelInfoModel > SPtr
QGraphicsScene of sensor-layout dots used by ChannelSelectionView for interactive channel picking.
Graphics item representing a selectable electrode or channel in a 2-D layout scene.
static bool readMNELoutFile(const QString &path, QMap< QString, QPointF > &channelData)
static bool makeLayout(const QList< QVector< float > > &inputPoints, QList< QVector< float > > &outputPoints, const QStringList &names, QFile &outFile, bool do_fit, float prad, float w, float h, bool writeFile=false, bool mirrorXAxis=false, bool mirrorYAxis=false)
static bool readBrainstormMonFile(QString path, QMultiMap< QString, QStringList > &selectionMap)
static bool writeBrainstormMonFiles(QString path, const QMultiMap< QString, QStringList > &selectionMap)
static bool readMNESelFile(QString path, QMultiMap< QString, QStringList > &selectionMap)
static bool writeMNESelFile(QString path, const QMultiMap< QString, QStringList > &selectionMap)