Skip to content

Commit

Permalink
fix #292631 fixed spanners (glissandos) layout
Browse files Browse the repository at this point in the history
  • Loading branch information
igorkorsukov committed Mar 26, 2020
1 parent dcb744c commit a2bfb02
Show file tree
Hide file tree
Showing 9 changed files with 71 additions and 47 deletions.
32 changes: 32 additions & 0 deletions libmscore/chord.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2546,6 +2546,38 @@ void Chord::layoutArpeggio2()
#endif
}

//---------------------------------------------------------
// layoutNotesSpanners
//---------------------------------------------------------

void Chord::layoutSpanners()
{
for (const Note* n : notes()) {
Tie* tie = n->tieFor();
if (tie)
tie->layout();
for (Spanner* sp : n->spannerBack())
sp->layout();
}
}

void Chord::layoutSpanners(System* system, const Fraction& stick)
{
//! REVIEW Needs explanation
for (const Note* note : notes()) {
Tie* t = note->tieFor();
if (t)
t->layoutFor(system);
t = note->tieBack();
if (t) {
if (t->startNote()->tick() < stick)
t->layoutBack(system);
}
for (Spanner* sp : note->spannerBack())
sp->layout();
}
}

//---------------------------------------------------------
// findNote
//---------------------------------------------------------
Expand Down
2 changes: 2 additions & 0 deletions libmscore/chord.h
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,8 @@ class Chord final : public ChordRest {
void layoutStem1() override;
void layoutStem();
void layoutArpeggio2();
void layoutSpanners();
void layoutSpanners(System* system, const Fraction& stick);

std::vector<Note*>& notes() { return _notes; }
const std::vector<Note*>& notes() const { return _notes; }
Expand Down
14 changes: 12 additions & 2 deletions libmscore/glissando.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@ NICE-TO-HAVE TODO:
and SlurSegment::changeAnchor() in slur.cpp as models)
*/

#include "log.h"

#include "arpeggio.h"
#include "glissando.h"
#include "chord.h"
Expand All @@ -29,6 +31,7 @@ NICE-TO-HAVE TODO:
#include "segment.h"
#include "staff.h"
#include "system.h"
#include "measure.h"
#include "style.h"
#include "sym.h"
#include "xml.h"
Expand Down Expand Up @@ -274,7 +277,7 @@ void Glissando::layout()

// FINAL SYSTEM-INITIAL NOTE
// if the last gliss. segment attaches to a system-initial note, some extra width has to be added
if (cr2->segment()->measure() == cr2->segment()->system()->firstMeasure() && cr2->rtick().isZero()
if (cr2->segment()->measure()->isFirstInSystem() && cr2->rtick().isZero()
// but ignore graces after, as they are not the first note of the system,
// even if their segment is the first segment of the system
&& !(cr2->noteType() == NoteType::GRACE8_AFTER
Expand Down Expand Up @@ -348,7 +351,14 @@ void Glissando::layout()

// compute glissando bbox as the bbox of the last segment, relative to the end anchor note
QPointF anchor2PagePos = anchor2->pagePos();
QPointF system2PagePos = cr2->segment()->system()->pagePos();
QPointF system2PagePos;
IF_ASSERT_FAILED(cr2->segment()->system()) {
system2PagePos = segm2->pos();
}
else {
system2PagePos = cr2->segment()->system()->pagePos();
}

QPointF anchor2SystPos = anchor2PagePos - system2PagePos;
QRectF r = QRectF(anchor2SystPos - segm2->pos(), anchor2SystPos - segm2->pos() - segm2->pos2()).normalized();
qreal lw = lineWidth() * .5;
Expand Down
2 changes: 1 addition & 1 deletion libmscore/keysig.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,7 @@ void KeySig::layout()


// Don't repeat naturals if shown in courtesy
if (measure() && measure()->system() && measure() == measure()->system()->firstMeasure()
if (measure() && measure()->system() && measure()->isFirstInSystem()
&& prevMeasure && prevMeasure->findSegment(SegmentType::KeySigAnnounce, tick())
&& !segment()->isKeySigAnnounceType())
naturalsOn = false;
Expand Down
16 changes: 2 additions & 14 deletions libmscore/layout.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4291,26 +4291,14 @@ void LayoutContext::collectPage()
for (Chord* cc : c->graceNotes()) {
if (cc->beam() && cc->beam()->elements().front() == cc)
cc->beam()->layout();
for (Note* n : cc->notes()) {
Tie* tie = n->tieFor();
if (tie)
tie->layout();
for (Spanner* sp : n->spannerFor())
sp->layout();
}
cc->layoutSpanners();
for (Element* element : cc->el()) {
if (element->isSlur())
element->layout();
}
}
c->layoutArpeggio2();
for (Note* n : c->notes()) {
Tie* tie = n->tieFor();
if (tie)
tie->layout();
for (Spanner* sp : n->spannerFor())
sp->layout();
}
c->layoutSpanners();
if (c->tremolo()) {
Tremolo* t = c->tremolo();
Chord* c1 = t->chord1();
Expand Down
16 changes: 2 additions & 14 deletions libmscore/layoutlinear.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -240,26 +240,14 @@ void LayoutContext::layoutLinear()
for (Chord* cc : c->graceNotes()) {
if (cc->beam() && cc->beam()->elements().front() == cc)
cc->beam()->layout();
for (Note* n : cc->notes()) {
Tie* tie = n->tieFor();
if (tie)
tie->layout();
for (Spanner* sp : n->spannerFor())
sp->layout();
}
cc->layoutSpanners();
for (Element* element : cc->el()) {
if (element->isSlur())
element->layout();
}
}
c->layoutArpeggio2();
for (Note* n : c->notes()) {
Tie* tie = n->tieFor();
if (tie)
tie->layout();
for (Spanner* sp : n->spannerFor())
sp->layout();
}
c->layoutSpanners();
if (c->tremolo()) {
Tremolo* t = c->tremolo();
Chord* c1 = t->chord1();
Expand Down
33 changes: 18 additions & 15 deletions libmscore/measure.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@
Implementation of most part of class Measure.
*/

#include "log.h"

#include "measure.h"
#include "accidental.h"
#include "ambitus.h"
Expand Down Expand Up @@ -486,7 +488,7 @@ void Measure::layoutMeasureNumber()
&& !irregular()
&& (no() || score()->styleB(Sid::showMeasureNumberOne))) {
if (score()->styleB(Sid::measureNumberSystem))
smn = (system()->firstMeasure() == this) || (prevMeasure() && prevMeasure()->irregular() && system()->firstMeasure() == prevMeasure());
smn = isFirstInSystem() || (prevMeasure() && prevMeasure()->irregular() && prevMeasure()->isFirstInSystem());
else {
smn = (no() == 0 && score()->styleB(Sid::showMeasureNumberOne)) ||
( ((no() + 1) % score()->styleI(Sid::measureNumberInterval)) == (score()->styleB(Sid::showMeasureNumberOne) ? 1 : 0) ) ||
Expand Down Expand Up @@ -658,18 +660,7 @@ void Measure::layout2()

if (cr->isChord()) {
Chord* c = toChord(cr);
for (const Note* note : c->notes()) {
Tie* t = note->tieFor();
if (t)
t->layoutFor(system());
t = note->tieBack();
if (t) {
if (t->startNote()->tick() < stick)
t->layoutBack(system());
}
for (Spanner* sp : note->spannerFor())
sp->layout();
}
c->layoutSpanners(system(), stick);
}
}
}
Expand Down Expand Up @@ -2515,6 +2506,18 @@ bool Measure::isAnacrusis() const
return irregular() && ticks() < Fraction::fromTicks(timeSig.ticksPerMeasure());
}

//---------------------------------------------------------
// isFirstInSystem
//---------------------------------------------------------

bool Measure::isFirstInSystem() const
{
IF_ASSERT_FAILED(system()) {
return false;
}
return system()->firstMeasure() == this;
}

//---------------------------------------------------------
// scanElements
//---------------------------------------------------------
Expand Down Expand Up @@ -4201,7 +4204,7 @@ void Measure::computeMinWidth(Segment* s, qreal x, bool isSystemHeader)
Segment* fs = firstEnabled();
if (!fs->visible()) // first enabled could be a clef change on invisible staff
fs = fs->nextActive();
bool first = system()->firstMeasure() == this;
bool first = isFirstInSystem();
const Shape ls(first ? QRectF(0.0, -1000000.0, 0.0, 2000000.0) : QRectF(0.0, 0.0, 0.0, spatium() * 4));

if (isMMRest()) {
Expand Down Expand Up @@ -4316,7 +4319,7 @@ void Measure::computeMinWidth()
return;
}
qreal x;
bool first = system()->firstMeasure() == this;
bool first = isFirstInSystem();

// left barriere:
// Make sure no elements crosses the left boarder if first measure in a system.
Expand Down
1 change: 1 addition & 0 deletions libmscore/measure.h
Original file line number Diff line number Diff line change
Expand Up @@ -218,6 +218,7 @@ class Measure final : public MeasureBase {
bool stemless(int staffIdx) const;
bool isFinalMeasureOfSection() const;
bool isAnacrusis() const;
bool isFirstInSystem() const;

bool breakMultiMeasureRest() const { return _breakMultiMeasureRest; }
void setBreakMultiMeasureRest(bool val) { _breakMultiMeasureRest = val; }
Expand Down
2 changes: 1 addition & 1 deletion libmscore/rehearsalmark.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ void RehearsalMark::layout()
Segment* repeat = m->findSegmentR(SegmentType::StartRepeatBarLine, Fraction(0, 1));
qreal barlineX = repeat ? repeat->x() - s->x() : measureX;
System* sys = m->system();
bool systemFirst = (sys && sys->firstMeasure() == m);
bool systemFirst = (sys && m->isFirstInSystem());

if (!header || repeat || !systemFirst) {
// no header, or header with repeat, or header mid-system - align with barline
Expand Down

0 comments on commit a2bfb02

Please sign in to comment.