123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268 |
- /*
- This file is part of QTau
- Copyright (C) 2013-2018 Tobias "Tomoko" Platen <tplaten@posteo.de>
- Copyright (C) 2013 digited <https://github.com/digited>
- Copyright (C) 2010-2013 HAL@ShurabaP <https://github.com/haruneko>
- QTau is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see <http://www.gnu.org/licenses/>.
- SPDX-License-Identifier: GPL-3.0+
- */
- #define __devloglevel__ 4
- #include "ui/dynDrawer.h"
- #include "ui/Config.h"
- #include "ui/noteEditor.h"
- // FIXME dynamics not supported yet, need synth/storeage support
- // scalars: VEL,
- #include <qevent.h>
- #include <QPainter>
- #include <QPixmap>
- #include "assert.h"
- #include "tempomap.h"
- #include <QDebug>
- #include <QTextEdit>
- #include <QVBoxLayout>
- // TODO: this class is a dummy
- qtauDynLabel::qtauDynLabel(const QString &txt, QWidget *parent)
- : QLabel(txt, parent), _state(off) {}
- qtauDynLabel::~qtauDynLabel() {}
- void qtauDynLabel::mousePressEvent(QMouseEvent *event) {
- if (event->button() == Qt::LeftButton)
- emit leftClicked();
- else if (event->button() == Qt::RightButton)
- emit rightClicked();
- }
- qtauDynLabel::EState qtauDynLabel::state() { return _state; }
- void qtauDynLabel::setState(EState s) { _state = s; }
- //===========================================================================
- #define SLIDE 5
- #define WIDTH 10
- qtauDynDrawer::qtauDynDrawer(qtauNoteEditor *qne, QWidget *parent)
- : QWidget(parent), _offset(0), _bgCache(nullptr) {
- _editor = qne;
- connect(_editor, &qtauNoteEditor::repaintDynDrawer, this,
- &qtauDynDrawer::onRepaintDynDrawer);
- }
- qtauDynDrawer::~qtauDynDrawer() {
- //
- }
- void qtauDynDrawer::onRepaintDynDrawer(void) { update(); }
- void qtauDynDrawer::setOffset(int off) {
- if (off != _offset) {
- _offset = off;
- update();
- }
- }
- void qtauDynDrawer::configure(const SNoteSetup &newSetup) {
- _ns = newSetup;
- updateCache();
- update();
- }
- //------------------------------------
- void qtauDynDrawer::paintEvent(QPaintEvent *event) {
- // draw bg
- int hSt = event->rect().x() + _offset;
- _hSt = hSt;
- int barWidth = _ns.note.width() * 4;
- int firstBar = hSt / barWidth;
- int cacheOffset = hSt - firstBar * barWidth;
- QRect screenRect(event->rect());
- QRect cacheRect(screenRect);
- cacheRect.moveLeft(cacheRect.x() + cacheOffset);
- QPainter p(this);
- p.drawPixmap(screenRect, *_bgCache, cacheRect);
- if (_velSelected) // draw vel
- {
- _h = event->rect().height();
- foreach (quint64 key, _editor->_notes.idMap.keys()) {
- qne::editorNote &n = _editor->_notes.idMap[key];
- double pulsesToPixels = (double)_ns.note.width() / c_midi_ppq;
- int notePos = n.pulseOffset * pulsesToPixels;
- notePos -= SLIDE;
- notePos -= hSt;
- float velocity = 100 / 128.0;
- if (key == _noteUnderCursor) velocity = _velocity;
- int width = WIDTH;
- int height = _h * (1 - velocity);
- QRect noteRect(notePos, _h, width, height - _h);
- if (key == _noteUnderCursor)
- p.fillRect(noteRect, QBrush(Qt::blue));
- else
- p.fillRect(noteRect, QBrush(Qt::green));
- }
- }
- }
- void qtauDynDrawer::resizeEvent(QResizeEvent *) { updateCache(); }
- // incomplete :: editing needs to be done
- void qtauDynDrawer::mouseDoubleClickEvent(QMouseEvent *) {
- _edit = new QTextEdit(this);
- // _edit->setGeometry(r);
- _edit->setVisible(true);
- _edit->setText("TODO");
- _edit->setFocus();
- _edit->selectAll();
- QVBoxLayout *layout = new QVBoxLayout;
- layout->addWidget(_edit);
- setLayout(layout);
- }
- void qtauDynDrawer::mouseMoveEvent(QMouseEvent *event) {
- (void)event;
- #if TODO
- //refactoring needed
- // if (!(_noteUnderCursor !=)) {
- if (event->x() > _notePos && event->x() < _notePos + WIDTH &&
- _velSelected) {
- _velocity = (_h - event->y()) / (1.0 * _h);
- // }
- update();
- }
- #endif
- }
- void qtauDynDrawer::mousePressEvent(QMouseEvent *event) {
- //
- if (_velSelected) // draw vel
- {
- foreach (quint64 key, _editor->_notes.idMap.keys()) {
- qne::editorNote &n = _editor->_notes.idMap[key];
- double pulsesToPixels = (double)_ns.note.width() / c_midi_ppq;
- int notePos = n.pulseOffset * pulsesToPixels;
- notePos -= SLIDE;
- notePos -= _hSt;
- if (event->x() > notePos && event->x() < notePos + WIDTH) {
- _noteUnderCursor = key;
- _notePos = notePos;
- update();
- }
- _velocity = (_h - event->y()) / (1.0 * _h);
- }
- }
- }
- void qtauDynDrawer::mouseReleaseEvent(QMouseEvent *) {
- _noteUnderCursor = -1;
- // if(_velSelected) updateModel()
- update();
- }
- void qtauDynDrawer::wheelEvent(QWheelEvent *event) {
- if (event->modifiers() & Qt::ControlModifier)
- emit zoomed(event->delta());
- else
- emit scrolled(event->delta());
- }
- void qtauDynDrawer::updateCache() {
- // DEVLOG_DEBUG("updateCache()");
- if (geometry().height() == 0) {
- DEVLOG_ERROR(
- "Zero height of dynDrawer in updateCache()... This definitely "
- "shouldn't happen.");
- return;
- }
- // bars fully fit in + 2 for partially visible bars
- int requiredCacheWidth =
- _ns.barScreenOffsets[_ns.numBars - 1] + _ns.note.width() * 8;
- if (!_bgCache || (_bgCache->width() < requiredCacheWidth ||
- _bgCache->height() < geometry().height())) {
- if (_bgCache) delete _bgCache;
- _bgCache = new QPixmap(requiredCacheWidth, geometry().height());
- }
- // prepare painting data
- int vSt = 0;
- int vEnd = geometry().height();
- int mSt = vEnd / 2 - 10;
- int mEnd = mSt + 20;
- int bar = 0;
- int beat = 0;
- int pxOff = 0;
- QVector<QPoint> noteLines;
- QVector<QPoint> barLines;
- assert(_ns.tmap);
- while (true) {
- if (pxOff >= requiredCacheWidth) break;
- fraction time = _ns.tmap->getTimeSignatureForBar(bar);
- if (beat == time.numerator) {
- barLines.append(QPoint(pxOff, vSt));
- barLines.append(QPoint(pxOff, vEnd));
- beat = 1;
- bar++;
- time = _ns.tmap->getTimeSignatureForBar(bar);
- } else {
- noteLines.append(QPoint(pxOff, mSt));
- noteLines.append(QPoint(pxOff, mEnd));
- beat++;
- }
- pxOff += _ns.note.width() * 4.0 / time.denominator;
- }
- // paint 'em!
- _bgCache->fill(Qt::white);
- QPainter p(_bgCache);
- p.setPen(QColor(cdef_color_inner_line));
- p.drawLines(noteLines);
- p.setPen(QColor(cdef_color_outer_line));
- p.drawLines(barLines);
- }
|