comparison layer/Colour3DPlotRenderer.cpp @ 1121:d930ff725f64 spectrogram-minor-refactor

Wiring through the magnitude range updates
author Chris Cannam
date Fri, 22 Jul 2016 12:17:55 +0100
parents 65cdaf8d6b50
children 94370157b265
comparison
equal deleted inserted replaced
1120:65cdaf8d6b50 1121:d930ff725f64
46 { 46 {
47 return render(v, paint, rect, true); 47 return render(v, paint, rect, true);
48 } 48 }
49 49
50 QRect 50 QRect
51 Colour3DPlotRenderer::getLargestUncachedRect() 51 Colour3DPlotRenderer::getLargestUncachedRect(const LayerGeometryProvider *v)
52 { 52 {
53 RenderType renderType = decideRenderType(v);
54
55 if (renderType == DirectTranslucent) {
56 return QRect(); // never cached
57 }
58
53 int h = m_cache.getSize().height(); 59 int h = m_cache.getSize().height();
54 60
55 QRect areaLeft(0, 0, m_cache.getValidLeft(), h); 61 QRect areaLeft(0, 0, m_cache.getValidLeft(), h);
56 QRect areaRight(m_cache.getValidRight(), 0, 62 QRect areaRight(m_cache.getValidRight(), 0,
57 m_cache.getSize().width() - m_cache.getValidRight(), h); 63 m_cache.getSize().width() - m_cache.getValidRight(), h);
89 95
90 m_magCache.resize(v->getPaintSize().width()); 96 m_magCache.resize(v->getPaintSize().width());
91 m_magCache.setZoomLevel(v->getZoomLevel()); 97 m_magCache.setZoomLevel(v->getZoomLevel());
92 98
93 if (renderType == DirectTranslucent) { 99 if (renderType == DirectTranslucent) {
94 renderDirectTranslucent(v, paint, rect); 100 MagnitudeRange range = renderDirectTranslucent(v, paint, rect);
95 //!!! mag range! 101 return { rect, range };
96
97 //!!! a dev debug check
98 if (!m_magCache.areColumnsSet(x0, x1 - x0)) {
99 cerr << "Columns (" << x0 << " -> " << x1-x0
100 << ") not set in mag cache" << endl;
101 throw std::logic_error("Columns not set in mag cache");
102 }
103
104 //!!! this is wrong
105 MagnitudeRange range = m_magCache.getRange(x0, x1-x0);
106
107 return { rect, range }; //!!! this return arg is not very useful
108 } 102 }
109 103
110 cerr << "cache start " << m_cache.getStartFrame() 104 cerr << "cache start " << m_cache.getStartFrame()
111 << " valid left " << m_cache.getValidLeft() 105 << " valid left " << m_cache.getValidLeft()
112 << " valid right " << m_cache.getValidRight() 106 << " valid right " << m_cache.getValidRight()
128 // cache is valid for the complete requested area 122 // cache is valid for the complete requested area
129 paint.drawImage(rect, m_cache.getImage(), rect); 123 paint.drawImage(rect, m_cache.getImage(), rect);
130 124
131 //!!! a dev debug check 125 //!!! a dev debug check
132 if (!m_magCache.areColumnsSet(x0, x1 - x0)) { 126 if (!m_magCache.areColumnsSet(x0, x1 - x0)) {
133 cerr << "Columns (" << x0 << " -> " << x1-x0 127 cerr << "NB Columns (" << x0 << " -> " << x1-x0
134 << ") not set in mag cache" << endl; 128 << ") not set in mag cache" << endl;
135 throw std::logic_error("Columns not set in mag cache"); 129 // throw std::logic_error("Columns not set in mag cache");
136 } 130 }
137 131
138 MagnitudeRange range = m_magCache.getRange(x0, x1-x0); 132 MagnitudeRange range = m_magCache.getRange(x0, x1-x0);
139 133
140 return { rect, range }; 134 return { rect, range };
229 throw std::logic_error("internal error: failed to render entire requested rect even when not time-constrained"); 223 throw std::logic_error("internal error: failed to render entire requested rect even when not time-constrained");
230 } 224 }
231 225
232 //!!! a dev debug check 226 //!!! a dev debug check
233 if (!m_magCache.areColumnsSet(x0, x1 - x0)) { 227 if (!m_magCache.areColumnsSet(x0, x1 - x0)) {
234 cerr << "Columns (" << x0 << " -> " << x1-x0 228 cerr << "NB Columns (" << x0 << " -> " << x1-x0
235 << ") not set in mag cache" << endl; 229 << ") not set in mag cache" << endl;
236 throw std::logic_error("Columns not set in mag cache"); 230 // throw std::logic_error("Columns not set in mag cache");
237 } 231 }
238 232
239 MagnitudeRange range = m_magCache.getRange(x0, x1-x0); 233 MagnitudeRange range = m_magCache.getRange(x0, x1-x0);
240 234
241 return { pr, range }; 235 return { pr, range };
296 } else { 290 } else {
297 return DrawBufferPixelResolution; 291 return DrawBufferPixelResolution;
298 } 292 }
299 } 293 }
300 294
301 void 295 MagnitudeRange
302 Colour3DPlotRenderer::renderDirectTranslucent(const LayerGeometryProvider *v, 296 Colour3DPlotRenderer::renderDirectTranslucent(const LayerGeometryProvider *v,
303 QPainter &paint, 297 QPainter &paint,
304 QRect rect) 298 QRect rect)
305 { 299 {
306 Profiler profiler("Colour3DPlotRenderer::renderDirectTranslucent"); 300 Profiler profiler("Colour3DPlotRenderer::renderDirectTranslucent");
307 301
302 MagnitudeRange magRange;
303
308 QPoint illuminatePos; 304 QPoint illuminatePos;
309 bool illuminate = v->shouldIlluminateLocalFeatures 305 bool illuminate = v->shouldIlluminateLocalFeatures
310 (m_sources.verticalBinLayer, illuminatePos); 306 (m_sources.verticalBinLayer, illuminatePos);
311 307
312 const DenseThreeDimensionalModel *model = m_sources.source; 308 const DenseThreeDimensionalModel *model = m_sources.source;
364 // << ", minbin " << minbin << ", maxbin " << maxbin << endl; 360 // << ", minbin " << minbin << ", maxbin " << maxbin << endl;
365 361
366 ColumnOp::Column column = 362 ColumnOp::Column column =
367 vector<float>(fullColumn.data() + minbin, 363 vector<float>(fullColumn.data() + minbin,
368 fullColumn.data() + maxbin + 1); 364 fullColumn.data() + maxbin + 1);
365
366 magRange.sample(column);
369 367
370 //!!! fft scale if (m_colourScale != ColourScaleType::Phase) { 368 //!!! fft scale if (m_colourScale != ColourScaleType::Phase) {
371 // column = ColumnOp::fftScale(column, m_fftSize); 369 // column = ColumnOp::fftScale(column, m_fftSize);
372 // } 370 // }
373 371
459 text, 457 text,
460 PaintAssistant::OutlinedText); 458 PaintAssistant::OutlinedText);
461 } 459 }
462 } 460 }
463 } 461 }
464 462
463 return magRange;
465 } 464 }
466 465
467 void 466 void
468 Colour3DPlotRenderer::renderToCachePixelResolution(const LayerGeometryProvider *v, 467 Colour3DPlotRenderer::renderToCachePixelResolution(const LayerGeometryProvider *v,
469 int x0, int repaintWidth, 468 int x0, int repaintWidth,
553 } 552 }
554 553
555 m_cache.drawImage(paintedLeft, attainedWidth, 554 m_cache.drawImage(paintedLeft, attainedWidth,
556 m_drawBuffer, 555 m_drawBuffer,
557 paintedLeft - x0, attainedWidth); 556 paintedLeft - x0, attainedWidth);
557
558 for (int i = 0; in_range_for(m_magRanges, i); ++i) {
559 m_magCache.sampleColumn(i, m_magRanges.at(i));
560 }
558 } 561 }
559 562
560 void 563 void
561 Colour3DPlotRenderer::renderToCacheBinResolution(const LayerGeometryProvider *v, 564 Colour3DPlotRenderer::renderToCacheBinResolution(const LayerGeometryProvider *v,
562 int x0, int repaintWidth) 565 int x0, int repaintWidth)
683 if (targetWidth > 0) { 686 if (targetWidth > 0) {
684 m_cache.drawImage(targetLeft, targetWidth, 687 m_cache.drawImage(targetLeft, targetWidth,
685 scaled, 688 scaled,
686 sourceLeft, sourceWidth); 689 sourceLeft, sourceWidth);
687 } 690 }
691
692 for (int i = 0; i < targetWidth; ++i) {
693 int sourceIx = int((double(i) / targetWidth) * sourceWidth);
694 if (in_range_for(m_magRanges, sourceIx)) {
695 m_magCache.sampleColumn(i, m_magRanges.at(sourceIx));
696 }
697 }
688 } 698 }
689 699
690 int 700 int
691 Colour3DPlotRenderer::renderDrawBuffer(int w, int h, 701 Colour3DPlotRenderer::renderDrawBuffer(int w, int h,
692 const vector<int> &binforx, 702 const vector<int> &binforx,
730 int columnCount = 0; 740 int columnCount = 0;
731 741
732 vector<float> preparedColumn; 742 vector<float> preparedColumn;
733 743
734 int modelWidth = sourceModel->getWidth(); 744 int modelWidth = sourceModel->getWidth();
735 cerr << "modelWidth " << modelWidth << endl; 745
736 746 cerr << "modelWidth " << modelWidth << ", divisor " << divisor << endl;
747
737 for (int x = start; x != finish; x += step) { 748 for (int x = start; x != finish; x += step) {
738 749
739 // x is the on-canvas pixel coord; sx (later) will be the 750 // x is the on-canvas pixel coord; sx (later) will be the
740 // source column index 751 // source column index
741 752
742 ++columnCount; 753 ++columnCount;
743 754
744 #ifdef DEBUG_SPECTROGRAM_REPAINT 755 #ifdef DEBUG_SPECTROGRAM_REPAINT
745 cerr << "x = " << x << endl; 756 cerr << "x = " << x << ", binforx[x] = " << binforx[x] << endl;
746 #endif 757 #endif
747 758
748 if (binforx[x] < 0) continue; 759 if (binforx[x] < 0) continue;
749 760
750 int sx0 = binforx[x] / divisor; 761 int sx0 = binforx[x] / divisor;
753 if (sx0 < 0) sx0 = sx1 - 1; 764 if (sx0 < 0) sx0 = sx1 - 1;
754 if (sx0 < 0) continue; 765 if (sx0 < 0) continue;
755 if (sx1 <= sx0) sx1 = sx0 + 1; 766 if (sx1 <= sx0) sx1 = sx0 + 1;
756 767
757 vector<float> pixelPeakColumn; 768 vector<float> pixelPeakColumn;
769 MagnitudeRange magRange;
758 770
759 for (int sx = sx0; sx < sx1; ++sx) { 771 for (int sx = sx0; sx < sx1; ++sx) {
760 772
761 #ifdef DEBUG_SPECTROGRAM_REPAINT 773 #ifdef DEBUG_SPECTROGRAM_REPAINT
762 cerr << "sx = " << sx << endl; 774 cerr << "sx = " << sx << endl;
784 796
785 //!!! fft scale if (m_colourScale != ColourScaleType::Phase) { 797 //!!! fft scale if (m_colourScale != ColourScaleType::Phase) {
786 // column = ColumnOp::fftScale(column, m_fftSize); 798 // column = ColumnOp::fftScale(column, m_fftSize);
787 // } 799 // }
788 800
789 MagnitudeRange r; 801 magRange.sample(column);
790 r.sample(column);
791 int magColIndex = sx - int(m_magCache.getStartFrame() /
792 sourceModel->getResolution());
793 cerr << "magColIndex = " << magColIndex << endl;
794 m_magCache.sampleColumn(magColIndex, r);
795 802
796 //!!! extents recordColumnExtents(column, 803 //!!! extents recordColumnExtents(column,
797 // sx, 804 // sx,
798 // overallMag, 805 // overallMag,
799 // overallMagChanged); 806 // overallMagChanged);
825 } 832 }
826 } 833 }
827 } 834 }
828 835
829 if (!pixelPeakColumn.empty()) { 836 if (!pixelPeakColumn.empty()) {
837
830 for (int y = 0; y < h; ++y) { 838 for (int y = 0; y < h; ++y) {
831 int py; 839 int py;
832 if (m_params.invertVertical) { 840 if (m_params.invertVertical) {
833 py = y; 841 py = y;
834 } else { 842 } else {
837 m_drawBuffer.setPixel 845 m_drawBuffer.setPixel
838 (x, 846 (x,
839 py, 847 py,
840 m_params.colourScale.getPixel(pixelPeakColumn[y])); 848 m_params.colourScale.getPixel(pixelPeakColumn[y]));
841 } 849 }
850
851 m_magRanges.push_back(magRange);
842 } 852 }
843 853
844 double fractionComplete = double(columnCount) / double(w); 854 double fractionComplete = double(columnCount) / double(w);
845 if (timer.outOfTime(fractionComplete)) { 855 if (timer.outOfTime(fractionComplete)) {
856 cerr << "out of time" << endl;
846 return columnCount; 857 return columnCount;
847 } 858 }
848 } 859 }
849 860
850 return columnCount; 861 return columnCount;
914 if (sx0 < 0) sx0 = sx1 - 1; 925 if (sx0 < 0) sx0 = sx1 - 1;
915 if (sx0 < 0) continue; 926 if (sx0 < 0) continue;
916 if (sx1 <= sx0) sx1 = sx0 + 1; 927 if (sx1 <= sx0) sx1 = sx0 + 1;
917 928
918 vector<float> pixelPeakColumn; 929 vector<float> pixelPeakColumn;
930 MagnitudeRange magRange;
919 931
920 for (int sx = sx0; sx < sx1; ++sx) { 932 for (int sx = sx0; sx < sx1; ++sx) {
921 933
922 if (sx < 0 || sx >= modelWidth) { 934 if (sx < 0 || sx >= modelWidth) {
923 continue; 935 continue;
929 941
930 ColumnOp::Column column = 942 ColumnOp::Column column =
931 vector<float>(fullColumn.data() + minbin, 943 vector<float>(fullColumn.data() + minbin,
932 fullColumn.data() + maxbin + 1); 944 fullColumn.data() + maxbin + 1);
933 945
946 magRange.sample(column);
947
934 //!!! fft scale if (m_colourScale != ColourScaleType::Phase) { 948 //!!! fft scale if (m_colourScale != ColourScaleType::Phase) {
935 // column = ColumnOp::fftScale(column, getFFTSize()); 949 // column = ColumnOp::fftScale(column, getFFTSize());
936 // } 950 // }
937 951
938 //!!! extents recordColumnExtents(column, 952 //!!! extents recordColumnExtents(column,
961 } 975 }
962 } 976 }
963 } 977 }
964 978
965 if (!pixelPeakColumn.empty()) { 979 if (!pixelPeakColumn.empty()) {
980
966 for (FFTModel::PeakSet::const_iterator pi = peakfreqs.begin(); 981 for (FFTModel::PeakSet::const_iterator pi = peakfreqs.begin();
967 pi != peakfreqs.end(); ++pi) { 982 pi != peakfreqs.end(); ++pi) {
968 983
969 int bin = pi->first; 984 int bin = pi->first;
970 double freq = pi->second; 985 double freq = pi->second;
983 m_drawBuffer.setPixel 998 m_drawBuffer.setPixel
984 (x, 999 (x,
985 iy, 1000 iy,
986 m_params.colourScale.getPixel(value)); 1001 m_params.colourScale.getPixel(value));
987 } 1002 }
1003
1004 m_magRanges.push_back(magRange);
988 } 1005 }
989 1006
990 double fractionComplete = double(columnCount) / double(w); 1007 double fractionComplete = double(columnCount) / double(w);
991 if (timer.outOfTime(fractionComplete)) { 1008 if (timer.outOfTime(fractionComplete)) {
992 return columnCount; 1009 return columnCount;
1007 m_params.colourScale.getColourForPixel 1024 m_params.colourScale.getColourForPixel
1008 (pixel, m_params.colourRotation).rgb()); 1025 (pixel, m_params.colourRotation).rgb());
1009 } 1026 }
1010 1027
1011 m_drawBuffer.fill(0); 1028 m_drawBuffer.fill(0);
1029 m_magRanges.clear();
1012 } 1030 }
1013 1031
1014 void 1032 void
1015 Colour3DPlotRenderer::clearDrawBuffer(int w, int h) 1033 Colour3DPlotRenderer::clearDrawBuffer(int w, int h)
1016 { 1034 {
1017 if (m_drawBuffer.width() < w || m_drawBuffer.height() != h) { 1035 if (m_drawBuffer.width() < w || m_drawBuffer.height() != h) {
1018 recreateDrawBuffer(w, h); 1036 recreateDrawBuffer(w, h);
1019 } else { 1037 } else {
1020 m_drawBuffer.fill(0); 1038 m_drawBuffer.fill(0);
1021 } 1039 m_magRanges.clear();
1022 } 1040 }
1023 1041 }
1024 1042
1043