1 #include <QtDebug>
2 #include <QColor>
3 #include <QDomNode>
4 #include <QPaintEvent>
5 #include <QPainter>
6 #include <QObject>
7 #include <QVector>
8 
9 #include "waveform/renderers/waveformrendermarkrange.h"
10 
11 #include "preferences/usersettings.h"
12 #include "track/track.h"
13 #include "waveform/renderers/waveformwidgetrenderer.h"
14 #include "widget/wskincolor.h"
15 #include "widget/wwidget.h"
16 #include "util/painterscope.h"
17 
WaveformRenderMarkRange(WaveformWidgetRenderer * waveformWidgetRenderer)18 WaveformRenderMarkRange::WaveformRenderMarkRange(WaveformWidgetRenderer* waveformWidgetRenderer) :
19     WaveformRendererAbstract(waveformWidgetRenderer) {
20 }
21 
setup(const QDomNode & node,const SkinContext & context)22 void WaveformRenderMarkRange::setup(const QDomNode& node, const SkinContext& context) {
23     m_markRanges.clear();
24     m_markRanges.reserve(1);
25 
26     QDomNode child = node.firstChild();
27     while (!child.isNull()) {
28         if (child.nodeName() == "MarkRange") {
29             m_markRanges.push_back(
30                     WaveformMarkRange(
31                             m_waveformRenderer->getGroup(),
32                             child,
33                             context,
34                             *m_waveformRenderer->getWaveformSignalColors()));
35         }
36         child = child.nextSibling();
37     }
38 }
39 
draw(QPainter * painter,QPaintEvent *)40 void WaveformRenderMarkRange::draw(QPainter *painter, QPaintEvent * /*event*/) {
41     PainterScope PainterScope(painter);
42 
43     painter->setWorldMatrixEnabled(false);
44 
45     if (isDirty()) {
46         generateImages();
47     }
48 
49     for (auto&& markRange: m_markRanges) {
50         // If the mark range is not active we should not draw it.
51         if (!markRange.active()) {
52             continue;
53         }
54 
55         // If the mark range is not visible we should not draw it.
56         if (!markRange.visible()) {
57             continue;
58         }
59 
60         // Active mark ranges by definition have starts/ends that are not
61         // disabled so no need to check.
62         double startSample = markRange.start();
63         double endSample = markRange.end();
64 
65         double startPosition = m_waveformRenderer->transformSamplePositionInRendererWorld(startSample);
66         double endPosition = m_waveformRenderer->transformSamplePositionInRendererWorld(endSample);
67 
68         //range not in the current display
69         if (startPosition > m_waveformRenderer->getLength() || endPosition < 0) {
70             continue;
71         }
72 
73         QImage* selectedImage = nullptr;
74 
75         selectedImage = markRange.enabled() ? &markRange.m_activeImage : &markRange.m_disabledImage;
76 
77         // draw the corresponding portion of the selected image
78         // this shouldn't involve *any* scaling it should be fast even in software mode
79         QRectF rect;
80         if (m_waveformRenderer->getOrientation() == Qt::Horizontal) {
81             rect.setRect(startPosition, 0, endPosition - startPosition, m_waveformRenderer->getHeight());
82         } else {
83             rect.setRect(0, startPosition, m_waveformRenderer->getWidth(), endPosition - startPosition);
84         }
85         painter->drawImage(rect, *selectedImage, rect);
86     }
87 }
88 
generateImages()89 void WaveformRenderMarkRange::generateImages() {
90     for (auto&& markRange: m_markRanges) {
91         markRange.generateImage(m_waveformRenderer->getWidth(), m_waveformRenderer->getHeight());
92     }
93     setDirty(false);
94 }
95