7 #include "uiMedDataQt/widget/SelectorModel.hpp" 9 #include "uiMedDataQt/InsertSeries.hpp" 11 #include <fwActivities/registry/Activities.hpp> 13 #include <fwData/Image.hpp> 15 #include <fwMedData/ActivitySeries.hpp> 16 #include <fwMedData/Equipment.hpp> 17 #include <fwMedData/ImageSeries.hpp> 18 #include <fwMedData/ModelSeries.hpp> 19 #include <fwMedData/Patient.hpp> 20 #include <fwMedData/Series.hpp> 22 #include <fwRuntime/operations.hpp> 24 #include <fwTools/fwID.hpp> 26 #include <boost/algorithm/string/trim.hpp> 27 #include <boost/math/special_functions/round.hpp> 28 #include <boost/regex.hpp> 31 #include <QStandardItem> 42 QStandardItemModel(parent),
57 void SelectorModel::init()
63 headers <<
"Patient name" <<
"Modality" <<
"Acquisition date" <<
"Image dimension" <<
"Voxel size" 64 <<
"Patient position" <<
"Study description" <<
"Patient ID" <<
"Age" 65 <<
"Referring physician / Performing physician " <<
"Sex" <<
"Birthdate" <<
"Institution";
66 this->setHorizontalHeaderLabels(headers);
80 QModelIndex idx = this->createIndex(index.row(), 0, index.internalPointer());
81 QStandardItem* item = this->itemFromIndex(idx);
89 this->QStandardItemModel::clear();
98 for(::fwData::Image::SpacingType::value_type val : spacing)
100 ::fwData::Image::SpacingType::value_type roundVal = ::boost::math::round(val * 100.)/100.;
101 roundSpacing.push_back(roundVal);
108 std::string formatDate(
const std::string& date)
110 std::string formatDate = date;
111 ::boost::algorithm::trim(formatDate);
113 const std::string regexYyear =
"[0-9]{4}";
114 const std::string regexMonth =
"[0-9]{2}";
115 const std::string regexDay =
"[0-9]{2}";
117 const std::string regexStr =
"("+regexYyear+
")"+
"("+regexMonth+
")"+
"("+regexDay+
")";
118 ::boost::regex re(regexStr);
119 ::boost::smatch match;
120 if( ::boost::regex_match(formatDate, match, re) )
122 std::string year, month, day, hour, min, sec;
123 OSLM_ASSERT(
"Wrong match for "<<formatDate, match.size() >= 4);
124 year.assign(match[1].first, match[1].second);
125 month.assign(match[2].first, match[2].second);
126 day.assign(match[3].first, match[3].second);
128 formatDate = year +
"/" + month +
"/" + day;
136 std::string formatTime(
const std::string& time)
138 std::string formatTime = time;
139 ::boost::algorithm::trim(formatTime);
141 const std::string regexHour =
"[0-9]{2}";
142 const std::string regexMin =
"[0-9]{2}";
143 const std::string regexSec =
"[0-9]{2}";
144 const std::string regexEnd =
"[.0-9]*";
146 const std::string regexStr =
"("+regexHour+
")"+
"("+regexMin+
")"+
"("+regexSec+
")"+regexEnd;
147 ::boost::regex re(regexStr);
148 ::boost::smatch match;
149 if( ::boost::regex_match(formatTime, match, re) )
151 std::string year, month, day, hour, min, sec;
152 OSLM_ASSERT(
"Wrong match for "<<formatTime, match.size() >= 4);
153 hour.assign(match[1].first, match[1].second);
154 min.assign(match[2].first, match[2].second);
155 sec.assign(match[3].first, match[3].second);
157 formatTime = hour +
":" + min +
":" + sec;
167 ::fwMedData::Study::sptr study = series->getStudy();
168 ::fwMedData::DicomValueType studyUID = study->getInstanceUID();
169 StudyUidItemMapType::iterator itr = m_items.find(studyUID);
170 QStandardItem* studyRootItem;
172 if(itr != m_items.end())
174 studyRootItem = itr->second;
178 ::fwMedData::Patient::sptr patient = series->getPatient();
179 ::fwMedData::Equipment::sptr equipment = series->getEquipment();
181 QStandardItem* patientName =
new QStandardItem( QString::fromStdString(patient->getName()) );
183 patientName->setData(QVariant(QString::fromStdString(study->getInstanceUID())),
UID);
184 QStandardItem* patientId =
new QStandardItem( QString::fromStdString(patient->getPatientId()) );
185 std::string birthDate = formatDate(patient->getBirthdate());
186 QStandardItem* patientBirthdate =
new QStandardItem( QString::fromStdString(birthDate) );
187 QStandardItem* patientSex =
new QStandardItem( QString::fromStdString(patient->getSex()) );
189 std::string studyDateTime = formatDate(study->getDate()) +
" " + formatTime(study->getTime());
190 QStandardItem* studyDate =
new QStandardItem( QString::fromStdString(studyDateTime));
191 QStandardItem* studyReferringPhysicianName =
new QStandardItem(
192 QString::fromStdString(study->getReferringPhysicianName()));
193 QStandardItem* studyDescription =
new QStandardItem( QString::fromStdString(study->getDescription()));
194 QStandardItem* studyPatientAge =
new QStandardItem( QString::fromStdString(study->getPatientAge()));
196 QStandardItem* institution =
new QStandardItem( QString::fromStdString(equipment->getInstitutionName()));
198 this->setItem(m_studyRowCount, 0, patientName);
199 this->setItem(m_studyRowCount, 1,
new QStandardItem());
200 this->setItem(m_studyRowCount, 2, studyDate);
201 this->setItem(m_studyRowCount, 3,
new QStandardItem());
202 this->setItem(m_studyRowCount, 4,
new QStandardItem());
203 this->setItem(m_studyRowCount, 5,
new QStandardItem());
204 this->setItem(m_studyRowCount, 6, studyDescription);
205 this->setItem(m_studyRowCount, 7, patientId);
206 this->setItem(m_studyRowCount, 8, studyPatientAge);
207 this->setItem(m_studyRowCount, 9, studyReferringPhysicianName);
208 this->setItem(m_studyRowCount, 10, patientSex);
209 this->setItem(m_studyRowCount, 11, patientBirthdate);
210 this->setItem(m_studyRowCount, 12, institution);
212 const int nbColumns = institution->index().column() + 1;
213 for (
int i = 0; i < nbColumns; ++i)
215 QStandardItem* item = this->item(m_studyRowCount, i);
216 item->setFlags(item->flags() & ~Qt::ItemIsSelectable );
220 studyRootItem = patientName;
221 m_items[studyUID] = studyRootItem;
224 QStandardItem* seriesModality =
new QStandardItem(QString::fromStdString(series->getModality()));
225 std::string seriesDateTime = formatDate(series->getDate()) +
" " + formatTime(series->getTime());
226 QStandardItem* seriesDate =
new QStandardItem( QString::fromStdString(seriesDateTime));
228 QStandardItem* seriesPerformingPhysician =
229 this->getInfo< ::fwMedData::DicomValuesType >(series->getPerformingPhysiciansName(),
", ");
231 QStandardItem* seriesDescription1 =
new QStandardItem(QString::fromStdString(series->getDescription()));
233 seriesDescription1->setData(QVariant(QString::fromStdString(series->getID())),
UID);
234 QStandardItem* seriesDescription2 =
new QStandardItem(QString::fromStdString(series->getDescription()));
236 const int nbRow = studyRootItem->rowCount();
237 studyRootItem->setChild(nbRow, 0, seriesDescription1);
238 studyRootItem->setChild(nbRow, 1, seriesModality);
239 studyRootItem->setChild(nbRow, 2, seriesDate);
240 studyRootItem->setChild(nbRow, 6, seriesDescription2);
241 studyRootItem->setChild(nbRow, 9, seriesPerformingPhysician);
242 studyRootItem->setChild(nbRow, 12,
new QStandardItem());
244 ::fwMedData::ImageSeries::sptr imageSeries = ::fwMedData::ImageSeries::dynamicCast(series);
248 ::fwData::Image::sptr image = imageSeries->getImage();
251 QStandardItem* imageSize = this->getInfo< ::fwData::Image::SizeType>(imageNumber,
" x ");
252 studyRootItem->setChild(nbRow, 3, imageSize);
255 QStandardItem* voxelSizeItem = this->getInfo< ::fwData::Image::SpacingType>(voxelSize,
" x ");
256 studyRootItem->setChild(nbRow, 4, voxelSizeItem);
259 QStandardItem* originItem = this->getInfo< ::fwData::Image::OriginType>(patientPosition,
", ");
260 studyRootItem->setChild(nbRow, 5, originItem);
265 ::uiMedDataQt::InsertSeries::sptr insertSeries = ::uiMedDataQt::InsertSeries::dynamicCast(series);
267 const int nbColumns = studyRootItem->columnCount();
268 for(
int i = 0; i < nbColumns; ++i)
270 QStandardItem* item = studyRootItem->child(nbRow, i);
273 studyRootItem->setChild(nbRow, i,
new QStandardItem());
274 item = studyRootItem->child(nbRow, i);
279 QFont f = item->font();
285 item->setFlags(item->flags() & ~Qt::ItemIsSelectable);
290 this->addSeriesIcon(series, seriesDescription1);
295 void SelectorModel::addSeriesIcon(::fwMedData::Series::sptr series, QStandardItem* item)
297 SeriesIconType::iterator iter = m_seriesIcons.find(series->getClassname());
298 if (iter != m_seriesIcons.end())
300 item->setIcon(QIcon(QString::fromStdString(iter->second)));
304 ::fwMedData::ImageSeries::sptr imageSeries = ::fwMedData::ImageSeries::dynamicCast(series);
305 ::fwMedData::ModelSeries::sptr modelSeries = ::fwMedData::ModelSeries::dynamicCast(series);
306 ::fwMedData::ActivitySeries::sptr activitySeries = ::fwMedData::ActivitySeries::dynamicCast(series);
309 const auto path = ::fwRuntime::getBundleResourceFilePath(
"media",
"icons/ImageSeries.svg");
310 item->setIcon(QIcon(QString::fromStdString(path.string())));
312 else if (modelSeries)
314 const auto path = ::fwRuntime::getBundleResourceFilePath(
"media",
"icons/ModelSeries.svg");
315 item->setIcon(QIcon(QString::fromStdString(path.string())));
317 else if (activitySeries)
320 std::string
id = activitySeries->getActivityConfigId();
321 OSLM_ASSERT(
"Activity information not found for" <<
id, registry->hasInfo(
id));
324 activityInfo = registry->getInfo(
id);
325 item->setIcon(QIcon(QString::fromStdString(activityInfo.icon)));
329 OSLM_WARN(
"This type of series is not defined (" << series->getClassname() <<
")");
339 this->removeSeriesItem(seriesItem);
346 QModelIndex idx = this->createIndex(index.row(), column, index.internalPointer());
354 QList<QStandardItem*> seriesItems;
355 QList<QStandardItem*> studyItems;
357 for(QModelIndex index : indexes)
359 SLM_ASSERT(
"Index must be in first column.", index.column() == 0);
360 QStandardItem* item = this->itemFromIndex(index);
363 studyItems.append(item);
367 seriesItems.append(item);
372 for(QStandardItem* item : seriesItems)
374 QStandardItem* studyItem = item->parent();
377 if (std::find(studyItems.begin(), studyItems.end(), studyItem) == studyItems.end())
379 this->removeSeriesItem(item);
384 for(QStandardItem* item : studyItems)
386 this->removeStudyItem(item);
392 bool SelectorModel::removeStudyItem(QStandardItem* item)
394 bool isRemoved =
false;
397 ::fwMedData::DicomValueType instanceUID = uid.toStdString();
399 isRemoved = this->QStandardItemModel::removeRow(item->row());
400 SLM_ASSERT(
"Remove can not be done!", isRemoved);
401 m_items.erase(instanceUID);
409 bool SelectorModel::removeSeriesItem(QStandardItem* item)
411 bool isRemoved =
false;
414 QStandardItem* parent = item->parent();
415 isRemoved = this->QStandardItemModel::removeRow(item->row(), this->indexFromItem(parent));
416 SLM_ASSERT(
"Remove can not be done!", isRemoved);
417 if(parent && parent->rowCount() == 0)
419 this->removeStudyItem(parent);
428 QStandardItem* seriesItem;
429 ::fwMedData::Study::sptr study = series->getStudy();
432 int nbRow = studyItem->rowCount();
433 for(
int row = 0; row < nbRow; ++row)
435 QStandardItem* child = studyItem->child(row);
437 if(seriesId == series->getID())
450 ::fwMedData::DicomValueType studyInstanceUid = study->getInstanceUID();
452 QStandardItem* studyItem = m_items[studyInstanceUid];
460 m_seriesIcons = seriesIcons;
The namespace uiMedDataQt contains editors for medical data.
Contains fwAtomsFilter::registry details.
Holds Activities configuration.
#define OSLM_ASSERT(message, cond)
work like 'assert' from 'cassert', with in addition a message logged by spylog (with FATAL loglevel) ...
static FWACTIVITIES_API Activities::sptr getDefault()
Return the default global instance of Activities.
#define OSLM_WARN(message)
#define SLM_ASSERT(message, cond)
work like 'assert' from 'cassert', with in addition a message logged by spylog (with FATAL loglevel) ...
std::vector< double > SpacingType
Image spacing type.
::fwData::Array::SizeType SizeType
Image size type.
std::vector< double > OriginType
Image origin type.