Skip to content

Commit

Permalink
move mp3 export out from score-media generation command
Browse files Browse the repository at this point in the history
Prevent score-media failures on big scores. See stskeeps/qtbase@e1d3687.

Use --score-mp3 to export mp3 as a json as well

Misc.: replace raw pointers with unique_ptr. Fix incorrect naming for the svg IO device.
  • Loading branch information
anatoly-os committed Dec 17, 2018
1 parent 316566f commit c63d1c4
Show file tree
Hide file tree
Showing 3 changed files with 93 additions and 43 deletions.
118 changes: 78 additions & 40 deletions mscore/file.cpp
Expand Up @@ -2973,6 +2973,10 @@ QPixmap MuseScore::extractThumbnail(const QString& name)
return pm;
}

//---------------------------------------------------------
// saveMetadataJSON
//---------------------------------------------------------

bool MuseScore::saveMetadataJSON(Score* score, const QString& name)
{
QFile f(name);
Expand All @@ -2985,7 +2989,7 @@ bool MuseScore::saveMetadataJSON(Score* score, const QString& name)
f.close();
return true;
}

QJsonObject MuseScore::saveMetadataJSON(Score* score)
{
auto boolToString = [](bool b) { return b ? "true" : "false"; };
Expand Down Expand Up @@ -3106,98 +3110,132 @@ QJsonObject MuseScore::saveMetadataJSON(Score* score)
return json;
}

bool MuseScore::exportAllMediaFiles(const QString& inFilePath, const QString& outFilePath)
//---------------------------------------------------------
// exportMp3AsJSON
//---------------------------------------------------------

bool MuseScore::exportMp3AsJSON(const QString& inFilePath, const QString& outFilePath)
{
MasterScore* score = mscore->readScore(inFilePath);
score->switchToPageMode();

QJsonObject jsonForMedia;
bool res = true;

std::unique_ptr<MasterScore> score(mscore->readScore(inFilePath));
if (!score)
return false;

//export score audio
QByteArray mp3Data;
QBuffer mp3Device(&mp3Data);
mp3Device.open(QIODevice::ReadWrite);
bool dummy = false;
res &= mscore->saveMp3(score, &mp3Device, dummy);
QJsonValue mp3Json(QString::fromLatin1(mp3Data.toBase64()));
mscore->saveMp3(score.get(), &mp3Device, dummy);

QJsonObject jsonForMedia;
jsonForMedia["mp3"] = QString::fromLatin1(mp3Data.toBase64());

QJsonDocument jsonDoc(jsonForMedia);
const QString& jsonPath{outFilePath};
QFile file(jsonPath);
file.open(QIODevice::WriteOnly);
file.write(jsonDoc.toJson(QJsonDocument::Compact));
file.close();
return true;
}

//---------------------------------------------------------
// exportAllMediaFiles
//---------------------------------------------------------

bool MuseScore::exportAllMediaFiles(const QString& inFilePath, const QString& outFilePath)
{
std::unique_ptr<MasterScore> score(mscore->readScore(inFilePath));
if (!score)
return false;

score->switchToPageMode();

//// JSON specification ///////////////////////////
//jsonForMedia["pngs"] = pngsJsonArray;
//jsonForMedia["mposXML"] = mposJson;
//jsonForMedia["sposXML"] = sposJson;
//jsonForMedia["pdf"] = pdfJson;
//jsonForMedia["svgs"] = svgsJsonArray;
//jsonForMedia["midi"] = midiJson;
//jsonForMedia["mxml"] = mxmlJson;
//jsonForMedia["metadata"] = mdJson;
///////////////////////////////////////////////////

QJsonObject jsonForMedia;
bool res = true;

{
//export score pngs and svgs
QJsonArray pngsJsonArray;
QJsonArray svgsJsonArray;
for (int i = 0; i < score->pages().size(); ++i) {
QByteArray pngData;
QBuffer pngDevice(&pngData);
pngDevice.open(QIODevice::ReadWrite);
res &= mscore->savePng(score, &pngDevice, i);
res &= mscore->savePng(score.get(), &pngDevice, i);
QJsonValue pngJson(QString::fromLatin1(pngData.toBase64()));
pngsJsonArray.append(pngJson);
QByteArray svgData;
QBuffer svgDevice(&svgData);
pngDevice.open(QIODevice::ReadWrite);
res &= mscore->saveSvg(score, &svgDevice, i);
svgDevice.open(QIODevice::ReadWrite);
res &= mscore->saveSvg(score.get(), &svgDevice, i);
QJsonValue svgJson(QString::fromLatin1(svgData.toBase64()));
svgsJsonArray.append(svgJson);
}

jsonForMedia["pngs"] = pngsJsonArray;
jsonForMedia["svgs"] = svgsJsonArray;
}

//export score .spos
QByteArray partDataPos;
QBuffer partPosDevice(&partDataPos);
partPosDevice.open(QIODevice::ReadWrite);
savePositions(score, &partPosDevice, true);
QJsonValue sposJson(QString::fromLatin1(partDataPos.toBase64()));
savePositions(score.get(), &partPosDevice, true);
jsonForMedia["sposXML"] = QString::fromLatin1(partDataPos.toBase64());
partPosDevice.close();
partDataPos.clear();

//export score .mpos
partPosDevice.open(QIODevice::ReadWrite);
savePositions(score, &partPosDevice, false);
QJsonValue mposJson(QString::fromLatin1(partDataPos.toBase64()));
savePositions(score.get(), &partPosDevice, false);
jsonForMedia["mposXML"] = QString::fromLatin1(partDataPos.toBase64());

//export score pdf
QByteArray pdfData;
QBuffer pdfDevice(&pdfData);
pdfDevice.open(QIODevice::ReadWrite);
QPdfWriter writer(&pdfDevice);
res &= mscore->savePdf(score, writer);
QJsonValue pdfJson(QString::fromLatin1(pdfData.toBase64()));
res &= mscore->savePdf(score.get(), writer);
jsonForMedia["pdf"] = QString::fromLatin1(pdfData.toBase64());

//export score midi
QByteArray midiData;
QBuffer midiDevice(&midiData);
midiDevice.open(QIODevice::ReadWrite);
res &= mscore->saveMidi(score, &midiDevice);
QJsonValue midiJson(QString::fromLatin1(midiData.toBase64()));
res &= mscore->saveMidi(score.get(), &midiDevice);
jsonForMedia["midi"] = QString::fromLatin1(midiData.toBase64());

//export musicxml
QByteArray mxmlData;
QBuffer mxmlDevice(&mxmlData);
mxmlDevice.open(QIODevice::ReadWrite);
res &= saveMxl(score, &mxmlDevice);
QJsonValue mxmlJson(QString::fromLatin1(mxmlData.toBase64()));
res &= saveMxl(score.get(), &mxmlDevice);
jsonForMedia["mxml"] = QString::fromLatin1(mxmlData.toBase64());

//export metadata
QJsonObject mdJson = mscore->saveMetadataJSON(score);
jsonForMedia["metadata"] = mscore->saveMetadataJSON(score.get());

//// JSON specification ///////////////////////////
jsonForMedia["mp3"] = mp3Json;
jsonForMedia["pngs"] = pngsJsonArray;
jsonForMedia["mposXML"] = mposJson;
jsonForMedia["sposXML"] = sposJson;
jsonForMedia["pdf"] = pdfJson;
jsonForMedia["svgs"] = svgsJsonArray;
jsonForMedia["midi"] = midiJson;
jsonForMedia["mxml"] = mxmlJson;
jsonForMedia["metadata"] = mdJson;
///////////////////////////////////////////////////
QJsonDocument jsonDoc(jsonForMedia);
const QString& jsonPath{outFilePath}; //{"D:\\123\\score.json"};
const QString& jsonPath{outFilePath};
QFile file(jsonPath);
file.open(QIODevice::WriteOnly);
if (!file.open(QIODevice::WriteOnly))
return false;

file.write(jsonDoc.toJson(QJsonDocument::Compact));
file.close();
delete score;
return true;

return res;
}

}
Expand Down
15 changes: 13 additions & 2 deletions mscore/musescore.cpp
Expand Up @@ -173,7 +173,8 @@ bool noWebView = false;
bool exportScoreParts = false;
bool ignoreWarnings = false;
bool exportScoreMedia = false;

bool exportScoreMp3 = false;

QString mscoreGlobalShare;

static QString outFileName;
Expand Down Expand Up @@ -3463,6 +3464,9 @@ static bool processNonGui(const QStringList& argv)
{
if (exportScoreMedia)
return mscore->exportAllMediaFiles(argv[0]);
else if (exportScoreMp3)
return mscore->exportMp3AsJSON(argv[0]);

if (pluginMode) {
loadScores(argv);
QString pn(pluginName);
Expand Down Expand Up @@ -6917,7 +6921,8 @@ int main(int argc, char* av[])
parser.addOption(QCommandLineOption({"f", "force"}, "Used with '-o <file>', ignore warnings reg. score being corrupted or from wrong version"));
parser.addOption(QCommandLineOption({"b", "bitrate"}, "Used with '-o <file>.mp3', sets bitrate, in kbps", "bitrate"));
parser.addOption(QCommandLineOption({"E", "install-extension"}, "Install an extension, load soundfont as default unless if -e is passed too", "extension file"));
parser.addOption(QCommandLineOption("score-media", "Export all media for a given score in a single JSON file and print it to std out"));
parser.addOption(QCommandLineOption("score-media", "Export all media (excepting mp3) for a given score in a single JSON file and print it to std out"));
parser.addOption(QCommandLineOption("score-mp3", "Generates mp3 for the given score and export the data to a single JSON file, print it to std out"));
parser.addOption(QCommandLineOption("raw-diff", "Print a raw diff for the given scores"));
parser.addOption(QCommandLineOption("diff", "Print a diff for the given scores"));

Expand Down Expand Up @@ -7063,6 +7068,12 @@ int main(int argc, char* av[])
MScore::noGui = true;
converterMode = true;
}

if (parser.isSet("score-mp3")) {
exportScoreMp3 = true;
MScore::noGui = true;
converterMode = true;
}

if (parser.isSet("raw-diff")) {
MScore::noGui = true;
Expand Down
3 changes: 2 additions & 1 deletion mscore/musescore.h
Expand Up @@ -724,7 +724,8 @@ class MuseScore : public QMainWindow, public MuseScoreCore {
QJsonObject saveMetadataJSON(Score*);

bool exportAllMediaFiles(const QString& inFilePath, const QString& outFilePath = "/dev/stdout");

bool exportMp3AsJSON(const QString& inFilePath, const QString& outFilePath = "/dev/stdout");

virtual void closeScore(Score* score);

void addTempo();
Expand Down

0 comments on commit c63d1c4

Please sign in to comment.