Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 9 additions & 1 deletion src/include/mx/api/OttavaData.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,14 @@ class OttavaStart
SpannerStart spannerStart;
OttavaType ottavaType;

OttavaStart() : spannerStart{}, ottavaType{OttavaType::unspecified}
// Octave-shift size fidelity knob. The size value (8 or 15) follows from ottavaType, so a
// 15ma/15mb line always writes size="15" while an 8va/8vb line omits the redundant, spec-
// default size="8". When true, the writer also emits that redundant size="8"; the reader sets
// it when the source spelled the attribute out. Leave false (the default) when authoring. It
// has no effect on a 15ma/15mb line, whose size is always written.
bool writeDefaultSize;

OttavaStart() : spannerStart{}, ottavaType{OttavaType::unspecified}, writeDefaultSize{false}
{
}
};
Expand All @@ -52,6 +59,7 @@ class OttavaStop
MXAPI_EQUALS_BEGIN(OttavaStart)
MXAPI_EQUALS_MEMBER(spannerStart)
MXAPI_EQUALS_MEMBER(ottavaType)
MXAPI_EQUALS_MEMBER(writeDefaultSize)
MXAPI_EQUALS_END;
MXAPI_NOT_EQUALS_AND_VECTORS(OttavaStart);

Expand Down
2 changes: 2 additions & 0 deletions src/private/mx/impl/DirectionReader.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -840,6 +840,8 @@ void DirectionReader::parseOctaveShift(const core::DirectionType &directionType)
api::OttavaStart start;
start.spannerStart = impl::getSpannerStart(octaveShift);
start.ottavaType = ottavaType;
const bool isEightLine = ottavaType == api::OttavaType::o8va || ottavaType == api::OttavaType::o8vb;
start.writeDefaultSize = isEightLine && octaveShift.size().has_value();
start.spannerStart.tickTimePosition = myCursor.tickTimePosition;
myOutDirectionData.ottavaStarts.emplace_back(std::move(start));
appendOrderedComponent(api::DirectionComponentKind::ottavaStart,
Expand Down
18 changes: 14 additions & 4 deletions src/private/mx/impl/DirectionWriter.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -399,32 +399,42 @@ void DirectionWriter::emitOttavaStart(const api::OttavaStart &ottavaStart, core:
os.setNumber(core::NumberLevel{*number});
}

int sizeValue = 8;

switch (ottavaStart.ottavaType)
{
case api::OttavaType::o15ma: {
os.setType(core::UpDownStopContinue::down());
os.setSize(15);
sizeValue = 15;
break;
}
case api::OttavaType::o15mb: {
os.setType(core::UpDownStopContinue::up());
os.setSize(15);
sizeValue = 15;
break;
}
case api::OttavaType::o8va: {
os.setType(core::UpDownStopContinue::down());
os.setSize(8);
sizeValue = 8;
break;
}
case api::OttavaType::o8vb: {
os.setType(core::UpDownStopContinue::up());
os.setSize(8);
sizeValue = 8;
break;
}
default:
break;
}

// size follows from ottavaType; a 15ma/15mb line's size encodes the two-octave shift, so it is
// always written, while the redundant default size="8" is emitted only when writeDefaultSize is
// set (the source spelled it out).
if (sizeValue != 8 || ottavaStart.writeDefaultSize)
{
os.setSize(sizeValue);
}

core::DirectionType dt{};
dt.setChoice(core::DirectionTypeChoice::octaveShift(os));
addDirectionType(std::move(dt), direction);
Expand Down
Loading