// PartialsFrameTableView class implementation // // The table view for 1 frame of the partials. // // QATSH Copyright 2009 Jean-Philippe MEURET #include #include "ATSMath.h" #include #include #include #include "ATSModelItems.h" #include "ATSModelManager.h" #include "ATSPartialsProxyModel.h" #include "ATSPartialsFrameProxyModel.h" #include "FrameAndDataProcessor.h" #include "PartialsFrameTableView.h" #include "ui_PartialsFrameTableView.h" PartialsFrameTableView::PartialsFrameTableView(QWidget *parent) : QFrame(parent), _pui(new Ui::PartialsFrameTableView), _pModelMgr(0) { _pui->setupUi(this); #if (QT_VERSION >= QT_VERSION_CHECK(5,0,0)) _pui->qtvPartials->horizontalHeader()->setSectionResizeMode(QHeaderView::Stretch); #else _pui->qtvPartials->horizontalHeader()->setResizeMode(QHeaderView::Stretch); #endif // Enable control value synchronization _bSynchronizeControls = true; } PartialsFrameTableView::~PartialsFrameTableView() { delete _pui; } void PartialsFrameTableView::setModelManager(ATSModelManager* pModelMgr) { _pModelMgr = pModelMgr; // Set table view model. _pui->qtvPartials->setModel(_pModelMgr->partialsFrameModel()); connect(_pui->qtvPartials->selectionModel(), SIGNAL(selectionChanged(const QItemSelection&, const QItemSelection&)), this, SLOT(onFrameSelectionChanged(const QItemSelection&, const QItemSelection&))); connect(_pModelMgr->partialsSelectionModel(), SIGNAL(selectionChanged(const QItemSelection&, const QItemSelection&)), this, SLOT(onSelectionChanged(const QItemSelection&, const QItemSelection&))); //std::cout << "PartialsFrameTableView::setModelManager" << std::endl; _nMaxFrameIndex = _pModelMgr->partialsFrameModel()->nbFrames() - 1; _dFrameDuration = _pModelMgr->partialsFrameModel()->frameDuration(); // Reset maximum value for sliders _pui->qsdCurrentIndex->setMaximum(_nMaxFrameIndex); // Reset maximum value for index spin-boxes _pui->qsbCurrentIndex->setMaximum(_nMaxFrameIndex); // Reset minimum/maximum/step value for time spin-boxes _pui->qsbCurrentStartTime->setSingleStep(_dFrameDuration); _pui->qsbCurrentStartTime->setMaximum(_nMaxFrameIndex*_dFrameDuration); _pui->qsbCurrentEndTime->setSingleStep(_dFrameDuration); _pui->qsbCurrentEndTime->setMinimum(_dFrameDuration); _pui->qsbCurrentEndTime->setMaximum((_nMaxFrameIndex+1)*_dFrameDuration); // Connect controls to local changed() slots for synchronisation connect(_pui->qsdCurrentIndex, SIGNAL(valueChanged(int)), this, SLOT(onCurrentIndexChanged(int))); connect(_pui->qsbCurrentIndex, SIGNAL(valueChanged(int)), this, SLOT(onCurrentIndexChanged(int))); connect(_pui->qsbCurrentStartTime, SIGNAL(valueChanged(double)), this, SLOT(onCurrentStartTimeChanged(double))); connect(_pui->qsbCurrentEndTime, SIGNAL(valueChanged(double)), this, SLOT(onCurrentEndTimeChanged(double))); // Connect add/remove partials buttons to local slots. connect(_pui->qpbAddPartial, SIGNAL(clicked()), this, SLOT(onAddPartial())); connect(_pui->qpbRemovePartial, SIGNAL(clicked()), this, SLOT(onRemovePartial())); } void PartialsFrameTableView::setFrameAndDataProcessor(FrameAndDataProcessor* pProcessor) { _pProcessor = pProcessor; } int PartialsFrameTableView::currentFrameIndex() const { return _pui->qsdCurrentIndex->value(); } void PartialsFrameTableView::onFrameSelectionChanged(const QItemSelection& qisSelected, const QItemSelection& qisDeselected) { // Here, we convert input ATSPartialsFrameModel (de)selections (from table view) // to an ATSPartialsModel selection, suitable for the partials graphics views. std::cout << "PartialsFrameTableView::onFrameSelectionChanged" << std::endl; // 1) Disconnect graphics views selection model change propagation to table view. disconnect(_pModelMgr->partialsSelectionModel(), SIGNAL(selectionChanged(const QItemSelection&, const QItemSelection&)), this, SLOT(onSelectionChanged(const QItemSelection&, const QItemSelection&))); // 2) Selection. // Map the input ATSPartialsFrameModel selection to an ATSPartialsModel selection. const QItemSelection qisSelParts = _pModelMgr->partialsFrameModel()->mapSelectionToSource(qisSelected); // Apply it to the graphics views selectionModel. _pModelMgr->partialsSelectionModel()->select(qisSelParts, QItemSelectionModel::Select); // 3) Deselection. // Map the input ATSPartialsFrameModel deselection to an ATSPartialsModel deselection. const QItemSelection qisDeselParts = _pModelMgr->partialsFrameModel()->mapSelectionToSource(qisDeselected); // Apply it to the graphics views selectionModel. _pModelMgr->partialsSelectionModel()->select(qisDeselParts, QItemSelectionModel::Deselect); // 4) Reconnect graphics views selection model change propagation to table view. connect(_pModelMgr->partialsSelectionModel(), SIGNAL(selectionChanged(const QItemSelection&, const QItemSelection&)), this, SLOT(onSelectionChanged(const QItemSelection&, const QItemSelection&))); } void PartialsFrameTableView::onSelectionChanged(const QItemSelection& qisSelected, const QItemSelection& qisDeselected) { // Here, we convert input ATSPartialsModel (de)selections (from graphics views) // to an ATSPartialsFrameModel selection, suitable for the table view. //std::cout << "PartialsFrameTableView::onSelectionChanged" << std::endl; // 1) Disconnect table view selection model change propagation to graphics views. disconnect(_pui->qtvPartials->selectionModel(), SIGNAL(selectionChanged(const QItemSelection&, const QItemSelection&)), this, SLOT(onFrameSelectionChanged(const QItemSelection&, const QItemSelection&))); // 2) Selection. // Map this ATSPartialsModel selection to an output ATSPartialsFrameModel selection. const QItemSelection qisSelPartsFrame = _pModelMgr->partialsFrameModel()->mapSelectionFromSource(qisSelected); // foreach (QModelIndex mi, qisSelPartsFrame.indexes()) // { // std::cout << "PartialsFrameTableView::onSelectionChanged : selected(PartsFrame) : " // << mi.row() << ',' << mi.column() // << ':' << static_cast(mi.internalPointer()) //->type() // << std::endl; // } //std::cout << "selPartsFrame=" << qisSelPartsFrame.count() << std::endl; // Apply it to the table view selectionModel. _pui->qtvPartials->selectionModel()->select(qisSelPartsFrame, QItemSelectionModel::Select); // 3) Deselection. // Map this ATSPartialsModel deselection to an output ATSPartialsFrameModel deselection. const QItemSelection qisDeselPartsFrame = _pModelMgr->partialsFrameModel()->mapSelectionFromSource(qisDeselected); //std::cout << "deselPartsFrame="<< qisDeselPartsFrame.count() << std::endl; // Apply it from the table view selectionModel. _pui->qtvPartials->selectionModel()->select(qisDeselPartsFrame, QItemSelectionModel::Deselect); // 3) Reconnect table view selection model change propagation to graphics views. connect(_pui->qtvPartials->selectionModel(), SIGNAL(selectionChanged(const QItemSelection&, const QItemSelection&)), this, SLOT(onFrameSelectionChanged(const QItemSelection&, const QItemSelection&))); } // Slots to synchronize control values =============================== void PartialsFrameTableView::onCurrentIndexChanged(int nNewIndex) { // Nothing to do if control synchronization is blocked. if (!_bSynchronizeControls) return; // Synchronize attached controls. _bSynchronizeControls = false; _pui->qsbCurrentIndex->setValue(nNewIndex); _pui->qsdCurrentIndex->setValue(nNewIndex); _pui->qsbCurrentStartTime->setValue(nNewIndex*_dFrameDuration); _pui->qsbCurrentEndTime->setValue((nNewIndex+1)*_dFrameDuration); _bSynchronizeControls = true; // Update model. _pModelMgr->partialsFrameModel()->setCurrentFrame(nNewIndex); // Notify the world in case usefull. emit currentFrameChanged(nNewIndex); } void PartialsFrameTableView::onCurrentStartTimeChanged(double dNewTime) { // Nothing to do if control synchronization is blocked. if (!_bSynchronizeControls) return; // Synchronize attached controls. _bSynchronizeControls = false; const int nFrameIndex = (int)round(dNewTime / _dFrameDuration); _pui->qsbCurrentIndex->setValue(nFrameIndex); _pui->qsdCurrentIndex->setValue(nFrameIndex); _pui->qsbCurrentEndTime->setValue(dNewTime + _dFrameDuration); _bSynchronizeControls = true; // Update model. _pModelMgr->partialsFrameModel()->setCurrentFrame(nFrameIndex); // Notify the world in case usefull. emit currentFrameChanged(nFrameIndex); } void PartialsFrameTableView::onCurrentEndTimeChanged(double dNewTime) { // Nothing to do if control synchronization is blocked. if (!_bSynchronizeControls) return; // Synchronize attached controls. _bSynchronizeControls = false; const int nFrameIndex = (int)round(dNewTime / _dFrameDuration) - 1; _pui->qsbCurrentIndex->setValue(nFrameIndex); _pui->qsdCurrentIndex->setValue(nFrameIndex); _pui->qsbCurrentStartTime->setValue(dNewTime - _dFrameDuration); _bSynchronizeControls = true; // Update model. _pModelMgr->partialsFrameModel()->setCurrentFrame(nFrameIndex); // Notify the world in case usefull. emit currentFrameChanged(nFrameIndex); } // Slots to add/remove partials ==================================== void PartialsFrameTableView::onAddPartial() { // Retrieve the index of 1st selected partial if any. const QModelIndexList qisSelParts = _pModelMgr->partialsSelectionModel()->selection().indexes(); QModelIndex qmi1stSelPart; // Invalid for the moment if (!qisSelParts.isEmpty()) qmi1stSelPart = qisSelParts[0]; // Add the partial as a copy (if any) of the 1st selected partial. _pModelMgr->partialsModel()->addPartial(qmi1stSelPart); } void PartialsFrameTableView::onRemovePartial() { // Retrieve the selected partial indexes if any. const QModelIndexList qlmiSelParts = _pModelMgr->partialsSelectionModel()->selection().indexes(); // Remove the selected partials if any. if (!qlmiSelParts.isEmpty()) _pModelMgr->partialsModel()->removePartials(qlmiSelParts); }