Exemplo n.º 1
0
void Dynamic::layout()
      {
      if (!readPos().isNull()) {
            if (score()->mscVersion() < 118) {
                  setReadPos(QPointF());
                  // hack: 1.2 boundingBoxes are a bit wider which results
                  // in symbols moved right
                  setUserXoffset(userOff().x() - spatium() * .6);
                  }
            }
      Text::layout();

      Segment* s = segment();
      for (int voice = 0; voice < VOICES; ++voice) {
            int t = (track() & ~0x3) + voice;
            Chord* c = static_cast<Chord*>(s->element(t));
            if (!c)
                  continue;
            if (c->type() == CHORD) {
                  qreal noteHeadWidth = score()->noteHeadWidth() * c->mag();
                  if (c->stem() && !c->up())  // stem down
                        rxpos() += noteHeadWidth * .25;  // center on stem + optical correction
                  else
                        rxpos() += noteHeadWidth * .5;   // center on note head
                  }
            else
                  rxpos() += c->width() * .5;
            break;
            }
      }
Exemplo n.º 2
0
void NoteEntryAction::mousePress(Staff* staff, int bar, const QPointF& pos)
{
    Clef* clef = staff->lastClefChange(bar);

    Voice* voice = staff->part()->voice(m_tool->voice());
    VoiceBar* vb = voice->bar(bar);

    // find element before which to insert the chord
    int before = 0;
    for (int i = 0; i < vb->elementCount(); i++) {
        VoiceElement* e = vb->element(i);
        if (e->x() >= pos.x()) break;
        before++;
    }

    int line = staff->line(pos.y());
    int pitch = 0, accidentals = 0;
    if (clef && !m_isRest) {
        pitch = clef->lineToPitch(line);
        // get correct accidentals for note
        KeySignature* ks = staff->lastKeySignatureChange(bar);
        if (ks) accidentals = ks->accidentals(pitch);
        for (int i = 0; i < before; i++) {
            Chord* c = dynamic_cast<Chord*>(vb->element(i));
            if (!c) continue;
            for (int n = 0; n < c->noteCount(); n++) {
                if (c->note(n)->pitch() == pitch) {
                    accidentals = c->note(n)->accidentals();
                }
            }
        }
    }

    Chord* join = NULL;
    if (before > 0) join = dynamic_cast<Chord*>(vb->element(before-1));
    if (join && join->x() + join->width() >= pos.x()) {
        if (clef && !m_isRest) {
            m_tool->addCommand(new AddNoteCommand(m_tool->shape(), join, staff, m_duration, pitch, accidentals));
        } else {
            m_tool->addCommand(new MakeRestCommand(m_tool->shape(), join));
        }
    } else {
        if (clef && !m_isRest) {
            m_tool->addCommand(new CreateChordCommand(m_tool->shape(), vb, staff, m_duration, before, pitch, accidentals));
        } else {
            m_tool->addCommand(new CreateChordCommand(m_tool->shape(), vb, staff, m_duration, before));
        }
    }
}
void AbstractNoteMusicAction::mousePress(Staff* staff, int barIdx, const QPointF& pos)
{
    Part* part = staff->part();
    Sheet* sheet = part->sheet();
    Bar* bar = sheet->bar(barIdx);
    
    Clef* clef = staff->lastClefChange(barIdx, 0);
    
    // loop over all noteheads
    qreal closestDist = 1e9;
    Note* closestNote = 0;
    Chord* chord = 0;
    
    // outer loop, loop over all voices
    for (int v = 0; v < part->voiceCount(); v++) {
        Voice* voice = part->voice(v);
        VoiceBar* vb = voice->bar(bar);
        
        // next loop over all chords
        for (int e = 0; e < vb->elementCount(); e++) {
            Chord* c = dynamic_cast<Chord*>(vb->element(e));
            if (!c) continue;
            
            qreal centerX = c->x() + (c->width() / 2);
            
            // check if it is a rest
            if (c->noteCount() == 0) {
                qreal centerY = c->y() + (c->height() / 2);
                qreal dist = sqrt(sqr(centerX - pos.x()) + sqr(centerY - pos.y()));
                if (dist < closestDist) {
                    closestDist = dist;
                    closestNote = NULL;
                    chord = c;
                }
            }
            
            // lastly loop over all noteheads
            for (int n = 0; n < c->noteCount(); n++) {
                Note* note = c->note(n);
                if (note->staff() != staff) continue;
                
                int line = clef->pitchToLine(note->pitch());
                qreal centerY = line * staff->lineSpacing() / 2;
                
                qreal dist = sqrt(sqr(centerX - pos.x()) + sqr(centerY - pos.y()));
                if (dist < closestDist) {
                    closestDist = dist;
                    closestNote = note;
                    chord = c;
                }
            }
        }
    }
    
    StaffElement* se = 0;
    for (int e = 0; e < bar->staffElementCount(staff); e++) {
        StaffElement* elem = bar->staffElement(staff, e);
        qreal centerX = elem->x() + (elem->width() / 2);
        qreal centerY = elem->y() + (elem->height() / 2);
        qreal dist = sqrt(sqr(centerX - pos.x()) + sqr(centerY - pos.y()));
        if (dist < closestDist) {
            se = elem;
            closestDist = dist;
        }
    }
    
    if (se) {
        mousePress(se, closestDist, pos);
    } else {
        mousePress(chord, closestNote, closestDist, pos);
    }
}