1 //=============================================================================
2 //  MuseScore
3 //  Linux Music Score Editor
4 //
5 //  Copyright (C) 2002-2009 Werner Schweer and others
6 //
7 //  This program is free software; you can redistribute it and/or modify
8 //  it under the terms of the GNU General Public License version 2.
9 //
10 //  This program is distributed in the hope that it will be useful,
11 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
12 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 //  GNU General Public License for more details.
14 //
15 //  You should have received a copy of the GNU General Public License
16 //  along with this program; if not, write to the Free Software
17 //  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 //=============================================================================
19 
20 #ifndef __TIMELINE_H__
21 #define __TIMELINE_H__
22 
23 #include "libmscore/select.h"
24 #include "scoreview.h"
25 #include <vector>
26 
27 namespace Ms {
28 
29 class Score;
30 class ScoreView;
31 class Page;
32 class Timeline;
33 class ViewRect;
34 
35 //---------------------------------------------------------
36 //   TDockWidget
37 //    modified QScrollArea for Timeline
38 //---------------------------------------------------------
39 
40 class TDockWidget : public QDockWidget {
41       Q_OBJECT
42 
43       QSplitter* _grid;
44 
45       virtual void closeEvent(QCloseEvent* event);
46       virtual void changeEvent(QEvent*);
47 
48    signals:
49       void closed(bool);
50 
51    public:
52       TDockWidget(QWidget* w = 0);
grid()53       QSplitter* grid() { return _grid; }
54       };
55 
56 //---------------------------------------------------------
57 //   TRowLabels
58 //---------------------------------------------------------
59 
60 class TRowLabels : public QGraphicsView {
61       Q_OBJECT
62 
63    public:
64       enum class MouseOverValue {
65             NONE,
66             MOVE_UP_ARROW,
67             MOVE_DOWN_ARROW,
68             MOVE_UP_DOWN_ARROW,
69             COLLAPSE_UP_ARROW,
70             COLLAPSE_DOWN_ARROW,
71             OPEN_EYE,
72             CLOSED_EYE
73             };
74 
75    private:
76       TDockWidget* _scrollArea { nullptr };
77       Timeline* parent { nullptr };
78 
79       QPoint _oldLoc;
80 
81       bool _dragging = false;
82 
83       std::vector<std::pair<QGraphicsItem*, int>> _metaLabels;
84       std::map<MouseOverValue, QPixmap*> _mouseoverMap;
85       std::tuple<QGraphicsPixmapItem*, MouseOverValue, unsigned> _oldItemInfo;
86 
87       virtual void resizeEvent(QResizeEvent*);
88       virtual void mousePressEvent(QMouseEvent* event);
89       virtual void mouseMoveEvent(QMouseEvent* event);
90       virtual void mouseReleaseEvent(QMouseEvent* event);
91       virtual void contextMenuEvent(QContextMenuEvent*) override;
92       virtual void leaveEvent(QEvent*);
93 
94    private slots:
95       void restrictScroll(int value);
96 
97    public slots:
98       void mouseOver(QPointF scenePt);
99 
100    signals:
101       void moved(QPointF p);
102       void swapMeta(unsigned r, bool up);
103       void requestContextMenu(QContextMenuEvent*);
104 
105    public:
106       TRowLabels(TDockWidget* dockWidget, Timeline* time, QGraphicsView* w = 0);
107       void updateLabels(std::vector<std::pair<QString, bool>> labels, int height);
108       QString cursorIsOn();
109       };
110 
111 //---------------------------------------------------------
112 //   TimelineTheme
113 //---------------------------------------------------------
114 
115 struct TimelineTheme {
116       QColor backgroundColor, labelsColor1, labelsColor2, labelsColor3, gridColor1, gridColor2;
117       QColor measureMetaColor, selectionColor, nonVisiblePenColor, nonVisibleBrushColor, colorBoxColor;
118       QColor metaValuePenColor, metaValueBrushColor;
119       };
120 
121 //---------------------------------------------------------
122 //   Timeline
123 //---------------------------------------------------------
124 
125 class Timeline : public QGraphicsView {
126       Q_OBJECT
127 
128    public:
129       enum class ItemType {
130             TYPE_UNKNOWN = 0,
131             TYPE_MEASURE,
132             TYPE_META,
133             };
134       Q_ENUM(ItemType);
135 
136    private:
137       static constexpr int keyItemType = 15;
138 
139       int _gridWidth = 20;
140       int _gridHeight = 20;
141       int _maxZoom = 50;
142       int _minZoom = 5;
143       int _spacing = 5;
144 
145       TimelineTheme _lightTheme, _darkTheme;
146 
147       std::tuple<int, qreal, Element*, Element*, bool> _repeatInfo;
148       std::tuple<QGraphicsItem*, int, QColor> _oldHoverInfo;
149 
150       std::map<BarLineType, QPixmap*> _barlines;
151       bool _isBarline { false };
152 
153       TDockWidget* _scrollArea { nullptr };
154       TRowLabels* _rowNames { nullptr };
155 
156       Score* _score { nullptr };
157       ScoreView* _cv { nullptr };
158 
159       int gridRows = 0;
160       int gridCols = 0;
161 
162       QGraphicsPathItem* nonVisiblePathItem = nullptr;
163       QGraphicsPathItem* visiblePathItem = nullptr;
164       QGraphicsPathItem* selectionItem = nullptr;
165 
166       QGraphicsRectItem* _selectionBox { nullptr };
167       std::vector<std::pair<QGraphicsItem*, int>> _metaRows;
168 
169       QPainterPath _selectionPath;
170       QRectF _oldSelectionRect;
171       bool _mousePressed { false };
172       QPoint _oldLoc;
173 
174       bool _collapsedMeta { false };
175 
176       std::vector<std::tuple<QString, void (Timeline::*)(Segment*, int*, int), bool>> _metas;
177       void tempoMeta(Segment* seg, int* stagger, int pos);
178       void timeMeta(Segment* seg, int* stagger, int pos);
179       void measureMeta(Segment*, int*, int pos);
180       void rehearsalMeta(Segment* seg, int* stagger, int pos);
181       void keyMeta(Segment* seg, int* stagger, int pos);
182       void barlineMeta(Segment* seg, int* stagger, int pos);
183       void jumpMarkerMeta(Segment* seg, int* stagger, int pos);
184 
185       bool addMetaValue(int x, int pos, QString metaText, int row, ElementType elementType, Element* element, Segment* seg, Measure* measure, QString tooltip = "");
186       void setMetaData(QGraphicsItem* gi, int staff, ElementType et, Measure* m, bool full_measure, Element* e, QGraphicsItem* pairItem = nullptr, Segment* seg = nullptr);
187       unsigned getMetaRow(QString targetText);
188 
189       int _globalMeasureNumber { 0 };
190       int _globalZValue        { 0 };
191 
192       // True if meta value was last clicked
193       bool _metaValue = false;
194       ViewState state = ViewState::NORMAL;
195 
196       virtual void mousePressEvent(QMouseEvent* event);
197       virtual void mouseMoveEvent(QMouseEvent* event);
198       virtual void mouseReleaseEvent(QMouseEvent*);
199       virtual void wheelEvent(QWheelEvent *event);
200       virtual void leaveEvent(QEvent*);
201       void showEvent(QShowEvent*) override;
202       virtual void changeEvent(QEvent*);
203 
204       unsigned correctMetaRow(unsigned row);
205       int correctStave(int stave);
206 
207       QList<Part*> getParts();
208 
getMeasureRect(int measureIndex,int row,int numMetas)209       QRectF getMeasureRect(int measureIndex, int row, int numMetas) { return QRectF(measureIndex * _gridWidth, _gridHeight * (row + numMetas) + 3, _gridWidth, _gridHeight); }
210       void clearScene();
211 
212       void updateGrid(int startMeasure = -1, int endMeasure = -1);
213 
214    private slots:
215       void handleScroll(int value);
216       void updateView();
217       void objectDestroyed(QObject*);
218 
219    public slots:
220       void changeSelection(SelState);
221       void mouseOver(QPointF pos);
222       void swapMeta(unsigned row, bool switchUp);
223       virtual void contextMenuEvent(QContextMenuEvent* event) override;
224       void requestInstrumentDialog();
225       void toggleMetaRow();
226       void updateTimelineTheme();
227 
228    signals:
229       void moved(QPointF);
230 
231    public:
232       Timeline(TDockWidget* dockWidget, QWidget* parent = nullptr);
233       int correctPart(int stave);
234 
235       void drawSelection();
236       void drawGrid(int globalRows, int globalCols, int startMeasure = 0, int endMeasure = -1);
237 
238       void setScore(Score* s);
239       void setScoreView(ScoreView* sv);
240 
241       int nstaves() const;
242 
243       int getWidth() const;
244       int getHeight() const;
245       const TimelineTheme& activeTheme() const;
246 
updateGridFull()247       void updateGridFull() { updateGrid(0, -1); }
updateGridView()248       void updateGridView() { updateGrid(-1, -1); }
249       void updateGridFromCmdState();
250 
251       QColor colorBox(QGraphicsRectItem* item);
252 
253       std::vector<std::pair<QString, bool>> getLabels();
254 
255       unsigned nmetas() const;
256 
collapsed()257       bool collapsed() { return _collapsedMeta; }
setCollapsed(bool st)258       void setCollapsed(bool st) { _collapsedMeta = st; }
259 
260       Staff* numToStaff(int staff);
261       void toggleShow(int staff);
262       QString cursorIsOn();
263       };
264 
265 
266 } // namespace Ms
267 
268 Q_DECLARE_METATYPE(Ms::TRowLabels::MouseOverValue);
269 
270 #endif
271