Mercurial > hg > svcore
comparison base/View.cpp @ 10:ec6886f0e673
* Fix update and play limits for play-selection mode when not looping
* Fix playback in loop mode when no selection -- but the GUI update for
this is still wrong on the flyback
* Various fixes and improvements to making selections, particularly during
playback
* Draw selection under non-opaque non-scrollable layers, so as to improve
cacheing
* Show selection limits as text when drawing selection
* Allow user to find missing audio files when loading session
* Cross-fade selections when in play-selection mode -- mostly. We don't
cross-fade on a processing block boundary, and unfortunately with short
selections the selection boundary is quite likely to coincide with a block
boundary.
author | Chris Cannam |
---|---|
date | Wed, 25 Jan 2006 17:46:28 +0000 |
parents | 73d85d19919f |
children | f67ddc287bc3 |
comparison
equal
deleted
inserted
replaced
9:73d85d19919f | 10:ec6886f0e673 |
---|---|
202 View::setStartFrame(long f) | 202 View::setStartFrame(long f) |
203 { | 203 { |
204 setCentreFrame(f + m_zoomLevel * (width() / 2)); | 204 setCentreFrame(f + m_zoomLevel * (width() / 2)); |
205 } | 205 } |
206 | 206 |
207 void | 207 bool |
208 View::setCentreFrame(size_t f, bool e) | 208 View::setCentreFrame(size_t f, bool e) |
209 { | 209 { |
210 bool changeVisible = false; | |
211 | |
210 if (m_centreFrame != f) { | 212 if (m_centreFrame != f) { |
211 | 213 |
212 int formerPixel = m_centreFrame / m_zoomLevel; | 214 int formerPixel = m_centreFrame / m_zoomLevel; |
213 | 215 |
214 m_centreFrame = f; | 216 m_centreFrame = f; |
219 | 221 |
220 #ifdef DEBUG_VIEW_WIDGET_PAINT | 222 #ifdef DEBUG_VIEW_WIDGET_PAINT |
221 std::cout << "View(" << this << ")::setCentreFrame: newPixel " << newPixel << ", formerPixel " << formerPixel << std::endl; | 223 std::cout << "View(" << this << ")::setCentreFrame: newPixel " << newPixel << ", formerPixel " << formerPixel << std::endl; |
222 #endif | 224 #endif |
223 update(); | 225 update(); |
226 | |
227 changeVisible = true; | |
224 } | 228 } |
225 | 229 |
226 if (e) emit centreFrameChanged(this, f, m_followPan); | 230 if (e) emit centreFrameChanged(this, f, m_followPan); |
227 } | 231 } |
232 | |
233 return changeVisible; | |
228 } | 234 } |
229 | 235 |
230 void | 236 void |
231 View::setZoomLevel(size_t z) | 237 View::setZoomLevel(size_t z) |
232 { | 238 { |
490 if (!visible) return; | 496 if (!visible) return; |
491 | 497 |
492 switch (m_followPlay) { | 498 switch (m_followPlay) { |
493 | 499 |
494 case PlaybackScrollContinuous: | 500 case PlaybackScrollContinuous: |
495 if (QApplication::mouseButtons() == Qt::NoButton) { | 501 if (QApplication::mouseButtons() == Qt::NoButton && |
502 QApplication::keyboardModifiers() == Qt::NoModifier) { | |
496 setCentreFrame(f, false); | 503 setCentreFrame(f, false); |
497 } | 504 } |
498 break; | 505 break; |
499 | 506 |
500 case PlaybackScrollPage: | 507 case PlaybackScrollPage: |
501 { | 508 { |
509 int xold = (long(oldPlayPointerFrame) - getStartFrame()) / m_zoomLevel; | |
510 repaint(xold - 1, 0, 3, height()); | |
511 | |
502 long w = width() * getZoomLevel(); | 512 long w = width() * getZoomLevel(); |
503 w -= w/5; | 513 w -= w/5; |
504 long sf = (f / w) * w - w/8; | 514 long sf = (f / w) * w - w/8; |
515 | |
516 if (m_manager && | |
517 m_manager->isPlaying() && | |
518 m_manager->getPlaySelectionMode()) { | |
519 ViewManager::SelectionList selections = m_manager->getSelections(); | |
520 if (!selections.empty()) { | |
521 size_t selectionStart = selections.begin()->getStartFrame(); | |
522 if (sf < long(selectionStart) - w / 10) { | |
523 sf = long(selectionStart) - w / 10; | |
524 } | |
525 } | |
526 } | |
527 | |
505 #ifdef DEBUG_VIEW_WIDGET_PAINT | 528 #ifdef DEBUG_VIEW_WIDGET_PAINT |
506 std::cerr << "PlaybackScrollPage: f = " << f << ", sf = " << sf << ", start frame " | 529 std::cerr << "PlaybackScrollPage: f = " << f << ", sf = " << sf << ", start frame " |
507 << getStartFrame() << std::endl; | 530 << getStartFrame() << std::endl; |
508 #endif | 531 #endif |
509 setCentreFrame(sf + width() * getZoomLevel() / 2, false); | 532 |
510 int xold = (long(oldPlayPointerFrame) - getStartFrame()) / m_zoomLevel; | 533 if (QApplication::mouseButtons() == Qt::NoButton && |
534 QApplication::keyboardModifiers() == Qt::NoModifier) { | |
535 bool changed = | |
536 setCentreFrame(sf + width() * getZoomLevel() / 2, false); | |
537 if (changed) { | |
538 xold = (long(oldPlayPointerFrame) - | |
539 getStartFrame()) / m_zoomLevel; | |
540 update(xold - 1, 0, 3, height()); | |
541 } | |
542 } | |
543 | |
511 int xnew = (long(m_playPointerFrame) - getStartFrame()) / m_zoomLevel; | 544 int xnew = (long(m_playPointerFrame) - getStartFrame()) / m_zoomLevel; |
512 update(xold - 1, 0, 3, height()); | |
513 update(xnew - 1, 0, 3, height()); | 545 update(xnew - 1, 0, 3, height()); |
546 | |
514 break; | 547 break; |
515 } | 548 } |
516 | 549 |
517 case PlaybackIgnore: | 550 case PlaybackIgnore: |
518 if (long(f) >= getStartFrame() && f < getEndFrame()) { | 551 if (long(f) >= getStartFrame() && f < getEndFrame()) { |
815 LayerList scrollables = getScrollableBackLayers(layersChanged); | 848 LayerList scrollables = getScrollableBackLayers(layersChanged); |
816 LayerList nonScrollables = getNonScrollableFrontLayers(layersChanged); | 849 LayerList nonScrollables = getNonScrollableFrontLayers(layersChanged); |
817 bool selectionCacheable = nonScrollables.empty(); | 850 bool selectionCacheable = nonScrollables.empty(); |
818 bool haveSelections = m_manager && !m_manager->getSelections().empty(); | 851 bool haveSelections = m_manager && !m_manager->getSelections().empty(); |
819 bool selectionDrawn = false; | 852 bool selectionDrawn = false; |
853 | |
854 if (!selectionCacheable) { | |
855 selectionCacheable = true; | |
856 for (LayerList::const_iterator i = nonScrollables.begin(); | |
857 i != nonScrollables.end(); ++i) { | |
858 if ((*i)->isLayerOpaque()) { | |
859 selectionCacheable = false; | |
860 break; | |
861 } | |
862 } | |
863 } | |
820 | 864 |
821 #ifdef DEBUG_VIEW_WIDGET_PAINT | 865 #ifdef DEBUG_VIEW_WIDGET_PAINT |
822 std::cerr << "View(" << this << ")::paintEvent: have " << scrollables.size() | 866 std::cerr << "View(" << this << ")::paintEvent: have " << scrollables.size() |
823 << " scrollable back layers and " << nonScrollables.size() | 867 << " scrollable back layers and " << nonScrollables.size() |
824 << " non-scrollable front layers" << std::endl; | 868 << " non-scrollable front layers" << std::endl; |
1042 | 1086 |
1043 paint.save(); | 1087 paint.save(); |
1044 paint.setPen(QColor(150, 150, 255)); | 1088 paint.setPen(QColor(150, 150, 255)); |
1045 paint.setBrush(QColor(150, 150, 255, 80)); | 1089 paint.setBrush(QColor(150, 150, 255, 80)); |
1046 | 1090 |
1091 int sampleRate = getModelsSampleRate(); | |
1092 | |
1093 const QFontMetrics &metrics = paint.fontMetrics(); | |
1094 | |
1047 for (ViewManager::SelectionList::iterator i = selections.begin(); | 1095 for (ViewManager::SelectionList::iterator i = selections.begin(); |
1048 i != selections.end(); ++i) { | 1096 i != selections.end(); ++i) { |
1049 | 1097 |
1050 int p0 = -1, p1 = -1; | 1098 int p0 = -1, p1 = -1; |
1051 | 1099 |
1052 if (int(i->getStartFrame()) >= getStartFrame()) { | 1100 p0 = (long(i->getStartFrame()) - getStartFrame()) / m_zoomLevel; |
1053 p0 = (i->getStartFrame() - getStartFrame()) / m_zoomLevel; | 1101 p1 = (long(i->getEndFrame()) - getStartFrame()) / m_zoomLevel; |
1054 } | 1102 |
1055 | 1103 if (p1 < 0 || p0 > width()) continue; |
1056 if (int(i->getEndFrame()) >= getStartFrame()) { | |
1057 p1 = (i->getEndFrame() - getStartFrame()) / m_zoomLevel; | |
1058 } | |
1059 | |
1060 if (p0 == -1 && p1 == -1) continue; | |
1061 | |
1062 if (p1 > width()) p1 = width() + 1; | |
1063 | 1104 |
1064 #ifdef DEBUG_VIEW_WIDGET_PAINT | 1105 #ifdef DEBUG_VIEW_WIDGET_PAINT |
1065 std::cerr << "View::drawSelections: " << p0 << ",-1 [" << (p1-p0) << "x" << (height()+1) << "]" << std::endl; | 1106 std::cerr << "View::drawSelections: " << p0 << ",-1 [" << (p1-p0) << "x" << (height()+1) << "]" << std::endl; |
1066 #endif | 1107 #endif |
1067 | 1108 |
1068 paint.drawRect(p0, -1, p1 - p0, height() + 1); | 1109 paint.drawRect(p0, -1, p1 - p0, height() + 1); |
1110 | |
1111 if (sampleRate && shouldLabelSelections()) { | |
1112 | |
1113 QString startText = QString("%1 / %2") | |
1114 .arg(QString::fromStdString | |
1115 (RealTime::frame2RealTime | |
1116 (i->getStartFrame(), sampleRate).toText(true))) | |
1117 .arg(i->getStartFrame()); | |
1118 | |
1119 QString endText = QString(" %1 / %2") | |
1120 .arg(QString::fromStdString | |
1121 (RealTime::frame2RealTime | |
1122 (i->getEndFrame(), sampleRate).toText(true))) | |
1123 .arg(i->getEndFrame()); | |
1124 | |
1125 QString durationText = QString("(%1 / %2) ") | |
1126 .arg(QString::fromStdString | |
1127 (RealTime::frame2RealTime | |
1128 (i->getEndFrame() - i->getStartFrame(), sampleRate) | |
1129 .toText(true))) | |
1130 .arg(i->getEndFrame() - i->getStartFrame()); | |
1131 | |
1132 int sw = metrics.width(startText), | |
1133 ew = metrics.width(endText), | |
1134 dw = metrics.width(durationText); | |
1135 | |
1136 int sy = metrics.ascent() + metrics.height() + 4; | |
1137 int ey = sy; | |
1138 int dy = sy + metrics.height(); | |
1139 | |
1140 int sx = p0 + 2; | |
1141 int ex = sx; | |
1142 int dx = sx; | |
1143 | |
1144 if (sw + ew > (p1 - p0)) { | |
1145 ey += metrics.height(); | |
1146 dy += metrics.height(); | |
1147 } | |
1148 | |
1149 if (ew < (p1 - p0)) { | |
1150 ex = p1 - 2 - ew; | |
1151 } | |
1152 | |
1153 if (dw < (p1 - p0)) { | |
1154 dx = p1 - 2 - dw; | |
1155 } | |
1156 | |
1157 paint.drawText(sx, sy, startText); | |
1158 paint.drawText(ex, ey, endText); | |
1159 paint.drawText(dx, dy, durationText); | |
1160 } | |
1069 } | 1161 } |
1070 | 1162 |
1071 paint.restore(); | 1163 paint.restore(); |
1072 } | 1164 } |
1073 | 1165 |