372 lines
14 KiB
C++
372 lines
14 KiB
C++
//=============================================================================
|
|
// MuseScore
|
|
// Linux Music Score Editor
|
|
// $Id: keyb.cpp 5658 2012-05-21 18:40:58Z wschweer $
|
|
//
|
|
// Copyright (C) 2002-2011 Werner Schweer and others
|
|
//
|
|
// This program is free software; you can redistribute it and/or modify
|
|
// it under the terms of the GNU General Public License version 2.
|
|
//
|
|
// 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, write to the Free Software
|
|
// Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
|
//=============================================================================
|
|
|
|
#include "scoreview.h"
|
|
#include "libmscore/note.h"
|
|
#include "libmscore/sym.h"
|
|
#include "libmscore/note.h"
|
|
#include "libmscore/score.h"
|
|
#include "libmscore/rest.h"
|
|
#include "libmscore/chord.h"
|
|
#include "libmscore/select.h"
|
|
#include "libmscore/input.h"
|
|
#include "libmscore/key.h"
|
|
#include "libmscore/measure.h"
|
|
#include "musescore.h"
|
|
#include "libmscore/slur.h"
|
|
#include "libmscore/tuplet.h"
|
|
#include "libmscore/text.h"
|
|
#include "libmscore/staff.h"
|
|
#include "libmscore/part.h"
|
|
#include "drumtools.h"
|
|
#include "preferences.h"
|
|
#include "libmscore/segment.h"
|
|
#include "libmscore/mscore.h"
|
|
#include "libmscore/stafftype.h"
|
|
#include "texttools.h"
|
|
|
|
namespace Ms {
|
|
|
|
#ifdef Q_OS_MAC
|
|
#define CONTROL_MODIFIER Qt::AltModifier
|
|
#else
|
|
#define CONTROL_MODIFIER Qt::ControlModifier
|
|
#endif
|
|
|
|
//---------------------------------------------------------
|
|
// Canvas::editCmd
|
|
//---------------------------------------------------------
|
|
|
|
void ScoreView::editCmd(const QString& cmd)
|
|
{
|
|
if (!editObject)
|
|
return;
|
|
|
|
if (editObject->type() == Element::Type::LYRICS) {
|
|
if (cmd == "next-lyric")
|
|
lyricsTab(false, true, false);
|
|
else if (cmd == "prev-lyric")
|
|
lyricsTab(true, true, false);
|
|
}
|
|
}
|
|
|
|
//---------------------------------------------------------
|
|
// editKeyLyrics
|
|
//---------------------------------------------------------
|
|
|
|
bool ScoreView::editKeyLyrics(QKeyEvent* ev)
|
|
{
|
|
int key = ev->key();
|
|
Qt::KeyboardModifiers modifiers = ev->modifiers();
|
|
QString s = ev->text();
|
|
bool ctrl = modifiers == Qt::ControlModifier;
|
|
|
|
switch(key) {
|
|
case Qt::Key_Space:
|
|
if (!(modifiers & CONTROL_MODIFIER)) {
|
|
// TODO: shift+tab events are filtered by qt
|
|
lyricsTab(modifiers & Qt::ShiftModifier, true, false);
|
|
}
|
|
else
|
|
return false;
|
|
break;
|
|
|
|
case Qt::Key_Left:
|
|
if (!ctrl && editObject->edit(this, curGrip, key, modifiers, s)) {
|
|
mscore->textTools()->updateTools();
|
|
_score->update();
|
|
mscore->endCmd();
|
|
}
|
|
else
|
|
lyricsTab(true, true, true); // go to previous lyrics
|
|
break;
|
|
case Qt::Key_Right:
|
|
if (!ctrl && editObject->edit(this, curGrip, key, modifiers, s)) {
|
|
mscore->textTools()->updateTools();
|
|
_score->update();
|
|
mscore->endCmd();
|
|
}
|
|
else
|
|
lyricsTab(false, false, true); // go to next lyrics
|
|
break;
|
|
case Qt::Key_Up:
|
|
lyricsUpDown(true, true);
|
|
break;
|
|
case Qt::Key_Down:
|
|
lyricsUpDown(false, true);
|
|
break;
|
|
case Qt::Key_Return:
|
|
lyricsReturn();
|
|
break;
|
|
default:
|
|
{
|
|
if(s == "-" && !(modifiers & CONTROL_MODIFIER))
|
|
lyricsMinus();
|
|
else if (s == "_" && !(modifiers & CONTROL_MODIFIER))
|
|
lyricsUnderscore();
|
|
else
|
|
return false;
|
|
}
|
|
}
|
|
return true;
|
|
}
|
|
|
|
//---------------------------------------------------------
|
|
// editKey
|
|
//---------------------------------------------------------
|
|
|
|
void ScoreView::editKey(QKeyEvent* ev)
|
|
{
|
|
if (ev->type() == QEvent::KeyRelease) {
|
|
auto modifiers = Qt::ControlModifier | Qt::ShiftModifier;
|
|
if (editObject && editObject->isText()
|
|
&& ((ev->modifiers() & modifiers) == 0)) {
|
|
Text* text = static_cast<Text*>(editObject);
|
|
text->endHexState();
|
|
ev->accept();
|
|
update();
|
|
}
|
|
return;
|
|
}
|
|
int key = ev->key();
|
|
Qt::KeyboardModifiers modifiers = ev->modifiers();
|
|
QString s = ev->text();
|
|
|
|
if (MScore::debugMode)
|
|
qDebug("keyPressEvent key 0x%02x(%c) mod 0x%04x <%s> nativeKey 0x%02x scancode %d",
|
|
key, key, int(modifiers), qPrintable(s), ev->nativeVirtualKey(), ev->nativeScanCode());
|
|
|
|
if (!editObject)
|
|
return;
|
|
|
|
if (editObject->type() == Element::Type::LYRICS) {
|
|
if (editKeyLyrics(ev)) {
|
|
ev->accept();
|
|
return;
|
|
}
|
|
}
|
|
else if (editObject->type() == Element::Type::HARMONY) {
|
|
/*
|
|
if (key == Qt::Key_Tab || key == Qt::Key_Backtab) {
|
|
harmonyTab(key == Qt::Key_Backtab ? true : (modifiers & Qt::ShiftModifier));
|
|
ev->accept();
|
|
return;
|
|
}
|
|
*/
|
|
if (key == Qt::Key_Space && !(modifiers & CONTROL_MODIFIER)) {
|
|
harmonyBeatsTab(true, modifiers & Qt::ShiftModifier);
|
|
ev->accept();
|
|
return;
|
|
}
|
|
/*
|
|
if (key == Qt::Key_Semicolon || key == Qt::Key_Colon) {
|
|
harmonyBeatsTab(false, key == Qt::Key_Colon);
|
|
ev->accept();
|
|
return;
|
|
}
|
|
if (key >= Qt::Key_1 && key <= Qt::Key_9 && (modifiers & CONTROL_MODIFIER)) {
|
|
int ticks = (MScore::division >> 4) << (key - Qt::Key_1);
|
|
harmonyTicksTab(ticks);
|
|
ev->accept();
|
|
return;
|
|
}
|
|
*/
|
|
}
|
|
else if (editObject->type() == Element::Type::FIGURED_BASS) {
|
|
int found = false;
|
|
if (key == Qt::Key_Space && !(modifiers & CONTROL_MODIFIER)) {
|
|
figuredBassTab(false, modifiers & Qt::ShiftModifier);
|
|
found = true;
|
|
}
|
|
/*
|
|
if (key == Qt::Key_Tab || key == Qt::Key_Backtab) {
|
|
figuredBassTab(true, key == Qt::Key_Backtab ? true : (modifiers & Qt::ShiftModifier) );
|
|
found = true;
|
|
}
|
|
if (key >= Qt::Key_1 && key <= Qt::Key_9 && (modifiers & CONTROL_MODIFIER)) {
|
|
int ticks = (MScore::division >> 4) << (key - Qt::Key_1);
|
|
figuredBassTicksTab(ticks);
|
|
found = true;
|
|
}
|
|
*/
|
|
if (found) {
|
|
ev->accept();
|
|
return;
|
|
}
|
|
}
|
|
|
|
if (!((modifiers & Qt::ShiftModifier) && (key == Qt::Key_Backtab))) {
|
|
if (editObject->edit(this, curGrip, key, modifiers, s)) {
|
|
if (editObject->isText())
|
|
mscore->textTools()->updateTools();
|
|
updateGrips();
|
|
ev->accept();
|
|
_score->update();
|
|
mscore->endCmd();
|
|
return;
|
|
}
|
|
if (editObject->isText() && (key == Qt::Key_Left || key == Qt::Key_Right)) {
|
|
ev->accept();
|
|
_score->end();
|
|
mscore->endCmd();
|
|
//return;
|
|
}
|
|
}
|
|
QPointF delta;
|
|
qreal _spatium = editObject->spatium();
|
|
|
|
qreal xval, yval;
|
|
if (editObject->type() == Element::Type::BEAM) {
|
|
xval = 0.25 * _spatium;
|
|
if (modifiers & Qt::ControlModifier)
|
|
xval = _spatium;
|
|
else if (modifiers & Qt::AltModifier)
|
|
xval = 4 * _spatium;
|
|
}
|
|
else {
|
|
xval = MScore::nudgeStep * _spatium;
|
|
if (modifiers & Qt::ControlModifier)
|
|
xval = MScore::nudgeStep10 * _spatium;
|
|
else if (modifiers & Qt::AltModifier)
|
|
xval = MScore::nudgeStep50 * _spatium;
|
|
}
|
|
yval = xval;
|
|
|
|
if (mscore->vRaster()) {
|
|
qreal vRaster = _spatium / MScore::vRaster();
|
|
if (yval < vRaster)
|
|
yval = vRaster;
|
|
}
|
|
if (mscore->hRaster()) {
|
|
qreal hRaster = _spatium / MScore::hRaster();
|
|
if (xval < hRaster)
|
|
xval = hRaster;
|
|
}
|
|
// TODO: if raster, then xval/yval should be multiple of raster
|
|
|
|
switch (key) {
|
|
case Qt::Key_Left:
|
|
delta = QPointF(-xval, 0);
|
|
break;
|
|
case Qt::Key_Right:
|
|
delta = QPointF(xval, 0);
|
|
break;
|
|
case Qt::Key_Up:
|
|
delta = QPointF(0, -yval);
|
|
break;
|
|
case Qt::Key_Down:
|
|
delta = QPointF(0, yval);
|
|
break;
|
|
default:
|
|
ev->ignore();
|
|
return;
|
|
}
|
|
EditData ed;
|
|
ed.curGrip = curGrip;
|
|
ed.delta = delta;
|
|
ed.view = this;
|
|
ed.hRaster = mscore->hRaster();
|
|
ed.vRaster = mscore->vRaster();
|
|
if (curGrip != Grip::NO_GRIP && int(curGrip) < grips)
|
|
ed.pos = grip[int(curGrip)].center() + delta;
|
|
editObject->editDrag(ed);
|
|
updateGrips();
|
|
_score->update();
|
|
mscore->endCmd();
|
|
mscore->updateInspector();
|
|
ev->accept();
|
|
}
|
|
|
|
//---------------------------------------------------------
|
|
// updateInputState
|
|
//---------------------------------------------------------
|
|
|
|
void MuseScore::updateInputState(Score* score)
|
|
{
|
|
InputState& is = score->inputState();
|
|
if (is.noteEntryMode()) {
|
|
Staff* staff = score->staff(is.track() / VOICES);
|
|
switch (staff->staffType()->group()) {
|
|
case StaffGroup::STANDARD:
|
|
changeState(STATE_NOTE_ENTRY_PITCHED);
|
|
break;
|
|
case StaffGroup::TAB:
|
|
changeState(STATE_NOTE_ENTRY_TAB);
|
|
break;
|
|
case StaffGroup::PERCUSSION:
|
|
changeState(STATE_NOTE_ENTRY_DRUM);
|
|
break;
|
|
}
|
|
}
|
|
|
|
getAction("pad-rest")->setChecked(is.rest());
|
|
getAction("pad-dot")->setChecked(is.duration().dots() == 1);
|
|
getAction("pad-dotdot")->setChecked(is.duration().dots() == 2);
|
|
if ((mscore->state() & STATE_NORMAL) | (mscore->state() & STATE_NOTE_ENTRY)) {
|
|
getAction("pad-dot")->setEnabled(true);
|
|
getAction("pad-dotdot")->setEnabled(true);
|
|
}
|
|
switch (is.duration().type()) {
|
|
case TDuration::DurationType::V_128TH:
|
|
getAction("pad-dot")->setChecked(false);
|
|
getAction("pad-dot")->setEnabled(false);
|
|
case TDuration::DurationType::V_64TH:
|
|
getAction("pad-dotdot")->setChecked(false);
|
|
getAction("pad-dotdot")->setEnabled(false);
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
|
|
getAction("note-longa")->setChecked(is.duration() == TDuration::DurationType::V_LONG);
|
|
getAction("note-breve")->setChecked(is.duration() == TDuration::DurationType::V_BREVE);
|
|
getAction("pad-note-1")->setChecked(is.duration() == TDuration::DurationType::V_WHOLE);
|
|
getAction("pad-note-2")->setChecked(is.duration() == TDuration::DurationType::V_HALF);
|
|
getAction("pad-note-4")->setChecked(is.duration() == TDuration::DurationType::V_QUARTER);
|
|
getAction("pad-note-8")->setChecked(is.duration() == TDuration::DurationType::V_EIGHTH);
|
|
getAction("pad-note-16")->setChecked(is.duration() == TDuration::DurationType::V_16TH);
|
|
getAction("pad-note-32")->setChecked(is.duration() == TDuration::DurationType::V_32ND);
|
|
getAction("pad-note-64")->setChecked(is.duration() == TDuration::DurationType::V_64TH);
|
|
getAction("pad-note-128")->setChecked(is.duration() == TDuration::DurationType::V_128TH);
|
|
|
|
// uncheck all voices if multi-selection
|
|
int voice = score->selection().isSingle() ? is.voice() : -1;
|
|
getAction("voice-1")->setChecked(voice == 0);
|
|
getAction("voice-2")->setChecked(voice == 1);
|
|
getAction("voice-3")->setChecked(voice == 2);
|
|
getAction("voice-4")->setChecked(voice == 3);
|
|
|
|
getAction("acciaccatura")->setChecked(is.noteType() == NoteType::ACCIACCATURA);
|
|
getAction("appoggiatura")->setChecked(is.noteType() == NoteType::APPOGGIATURA);
|
|
getAction("grace4")->setChecked(is.noteType() == NoteType::GRACE4);
|
|
getAction("grace16")->setChecked(is.noteType() == NoteType::GRACE16);
|
|
getAction("grace32")->setChecked(is.noteType() == NoteType::GRACE32);
|
|
getAction("grace8after")->setChecked(is.noteType() == NoteType::GRACE8_AFTER);
|
|
getAction("grace16after")->setChecked(is.noteType() == NoteType::GRACE16_AFTER);
|
|
getAction("grace32after")->setChecked(is.noteType() == NoteType::GRACE32_AFTER);
|
|
getAction("beam-start")->setChecked(is.beamMode() == Beam::Mode::BEGIN);
|
|
getAction("beam-mid")->setChecked(is.beamMode() == Beam::Mode::MID);
|
|
getAction("no-beam")->setChecked(is.beamMode() == Beam::Mode::NONE);
|
|
getAction("beam32")->setChecked(is.beamMode() == Beam::Mode::BEGIN32);
|
|
getAction("auto-beam")->setChecked(is.beamMode() == Beam::Mode::AUTO);
|
|
getAction("repitch")->setChecked(is.repitchMode());
|
|
}
|
|
}
|
|
|